diff options
Diffstat (limited to 'Source/WebKit2/WebProcess')
77 files changed, 2272 insertions, 552 deletions
diff --git a/Source/WebKit2/WebProcess/Authentication/mac/AuthenticationManager.mac.mm b/Source/WebKit2/WebProcess/Authentication/mac/AuthenticationManager.mac.mm index c0b92f12b..1a772c3c5 100644 --- a/Source/WebKit2/WebProcess/Authentication/mac/AuthenticationManager.mac.mm +++ b/Source/WebKit2/WebProcess/Authentication/mac/AuthenticationManager.mac.mm @@ -38,6 +38,9 @@ namespace WebKit { bool AuthenticationManager::tryUsePlatformCertificateInfoForChallenge(const AuthenticationChallenge& challenge, const PlatformCertificateInfo& certificateInfo) { + // FIXME (NetworkProcess): This occurs in the WebProcess and therefore won't work. + // We need this to happen in the NetworkProcess. + CFArrayRef chain = certificateInfo.certificateChain(); if (!chain) return false; diff --git a/Source/WebKit2/WebProcess/Cookies/cf/WebCookieManagerCFNet.cpp b/Source/WebKit2/WebProcess/Cookies/cf/WebCookieManagerCFNet.cpp index 6606897d9..7137f63da 100644 --- a/Source/WebKit2/WebProcess/Cookies/cf/WebCookieManagerCFNet.cpp +++ b/Source/WebKit2/WebProcess/Cookies/cf/WebCookieManagerCFNet.cpp @@ -50,14 +50,22 @@ void WebCookieManager::platformSetHTTPCookieAcceptPolicy(HTTPCookieAcceptPolicy CFHTTPCookieStorageSetCookieAcceptPolicy(defaultCookieStorage, policy); + ASSERT_NOT_REACHED(); +#if NEEDS_FIXING_AFTER_R134960 if (RetainPtr<CFHTTPCookieStorageRef> cookieStorage = currentCFHTTPCookieStorage()) CFHTTPCookieStorageSetCookieAcceptPolicy(cookieStorage.get(), policy); +#endif } HTTPCookieAcceptPolicy WebCookieManager::platformGetHTTPCookieAcceptPolicy() { + ASSERT_NOT_REACHED(); +#if NEEDS_FIXING_AFTER_R134960 RetainPtr<CFHTTPCookieStorageRef> cookieStorage = currentCFHTTPCookieStorage(); return CFHTTPCookieStorageGetCookieAcceptPolicy(cookieStorage.get()); +#else + return 0; +#endif } } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/Cookies/mac/WebCookieManagerMac.mm b/Source/WebKit2/WebProcess/Cookies/mac/WebCookieManagerMac.mm index 0584307d6..6b9fe97ed 100644 --- a/Source/WebKit2/WebProcess/Cookies/mac/WebCookieManagerMac.mm +++ b/Source/WebKit2/WebProcess/Cookies/mac/WebCookieManagerMac.mm @@ -25,8 +25,8 @@ #import "config.h" #import "WebCookieManager.h" -#import <WebCore/CookieStorageCFNet.h> -#import <WebKitSystemInterface.h> + +#import "WebFrameNetworkingContext.h" using namespace WebCore; @@ -34,10 +34,7 @@ namespace WebKit { void WebCookieManager::platformSetHTTPCookieAcceptPolicy(HTTPCookieAcceptPolicy policy) { - [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookieAcceptPolicy:static_cast<NSHTTPCookieAcceptPolicy>(policy)]; - - if (RetainPtr<CFHTTPCookieStorageRef> cookieStorage = currentCFHTTPCookieStorage()) - WKSetHTTPCookieAcceptPolicy(cookieStorage.get(), policy); + WebFrameNetworkingContext::setCookieAcceptPolicyForAllContexts(policy); } HTTPCookieAcceptPolicy WebCookieManager::platformGetHTTPCookieAcceptPolicy() diff --git a/Source/WebKit2/WebProcess/Downloads/mac/DownloadMac.mm b/Source/WebKit2/WebProcess/Downloads/mac/DownloadMac.mm index 601d013c7..83108b182 100644 --- a/Source/WebKit2/WebProcess/Downloads/mac/DownloadMac.mm +++ b/Source/WebKit2/WebProcess/Downloads/mac/DownloadMac.mm @@ -109,6 +109,7 @@ void Download::platformDidFinish() { } +// FIXME (NetworkProcess): Downloads and their credentials have to go through the NetworkProcess void Download::receivedCredential(const AuthenticationChallenge& authenticationChallenge, const Credential& credential) { [authenticationChallenge.sender() useCredential:mac(credential) forAuthenticationChallenge:authenticationChallenge.nsURLAuthenticationChallenge()]; diff --git a/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFrame.cpp b/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFrame.cpp index f00e03539..55c29279e 100644 --- a/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFrame.cpp +++ b/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFrame.cpp @@ -199,6 +199,11 @@ bool WKBundleFrameAllowsFollowingLink(WKBundleFrameRef frameRef, WKURLRef urlRef return toImpl(frameRef)->allowsFollowingLink(WebCore::KURL(WebCore::KURL(), toWTFString(urlRef))); } +bool WKBundleFrameHandlesPageScaleGesture(WKBundleFrameRef frameRef) +{ + return toAPI(toImpl(frameRef)->handlesPageScaleGesture()); +} + WKRect WKBundleFrameGetContentBounds(WKBundleFrameRef frameRef) { return toAPI(toImpl(frameRef)->contentBounds()); diff --git a/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFramePrivate.h b/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFramePrivate.h index d2286ff89..b7aeaf978 100644 --- a/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFramePrivate.h +++ b/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleFramePrivate.h @@ -57,6 +57,8 @@ WK_EXPORT bool WKBundleFrameCallShouldCloseOnWebView(WKBundleFrameRef frame); WK_EXPORT WKBundleHitTestResultRef WKBundleFrameCreateHitTestResult(WKBundleFrameRef frame, WKPoint point); +WK_EXPORT bool WKBundleFrameHandlesPageScaleGesture(WKBundleFrameRef frame); + #ifdef __cplusplus } #endif diff --git a/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundle.cpp b/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundle.cpp index 82c122036..317911a9d 100644 --- a/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundle.cpp +++ b/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundle.cpp @@ -40,6 +40,7 @@ #include "WebCoreArgumentCoders.h" #include "WebDatabaseManager.h" #include "WebFrame.h" +#include "WebFrameNetworkingContext.h" #include "WebPage.h" #include "WebPreferencesStore.h" #include "WebProcess.h" @@ -268,6 +269,12 @@ void InjectedBundle::setJavaScriptCanAccessClipboard(WebPageGroupProxy* pageGrou void InjectedBundle::setPrivateBrowsingEnabled(WebPageGroupProxy* pageGroup, bool enabled) { +#if (PLATFORM(MAC) || USE(CFNETWORK)) && !PLATFORM(WIN) + if (enabled) + WebFrameNetworkingContext::ensurePrivateBrowsingSession(); + else + WebFrameNetworkingContext::destroyPrivateBrowsingSession(); +#endif const HashSet<Page*>& pages = PageGroup::pageGroup(pageGroup->identifier())->pages(); for (HashSet<Page*>::iterator iter = pages.begin(); iter != pages.end(); ++iter) (*iter)->settings()->setPrivateBrowsingEnabled(enabled); @@ -283,11 +290,9 @@ void InjectedBundle::setPopupBlockingEnabled(WebPageGroupProxy* pageGroup, bool void InjectedBundle::switchNetworkLoaderToNewTestingSession() { -#if PLATFORM(MAC) || USE(CFNETWORK) - // Set a private session for testing to avoid interfering with global cookies. This should be different from private browsing session. +#if (PLATFORM(MAC) || USE(CFNETWORK)) && !PLATFORM(WIN) // FIXME (NetworkProcess): Do this in network process, too. - RetainPtr<CFURLStorageSessionRef> session = ResourceHandle::createPrivateBrowsingStorageSession(CFSTR("Private WebKit Session")); - ResourceHandle::setDefaultStorageSession(session.get()); + WebFrameNetworkingContext::switchToNewTestingSession(); #endif } diff --git a/Source/WebKit2/WebProcess/Network/CustomProtocols/CustomProtocolManager.h b/Source/WebKit2/WebProcess/Network/CustomProtocols/CustomProtocolManager.h new file mode 100644 index 000000000..cb2453a87 --- /dev/null +++ b/Source/WebKit2/WebProcess/Network/CustomProtocols/CustomProtocolManager.h @@ -0,0 +1,94 @@ +/* + * Copyright (C) 2012 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef CustomProtocolManager_h +#define CustomProtocolManager_h + +#if ENABLE(CUSTOM_PROTOCOLS) + +#include "MessageID.h" +#include <wtf/HashSet.h> +#include <wtf/text/WTFString.h> + +#if PLATFORM(MAC) +#include <wtf/HashMap.h> +#include <wtf/RetainPtr.h> +OBJC_CLASS WKCustomProtocol; +#endif + + +namespace CoreIPC { +class Connection; +class DataReference; +class MessageDecoder; +} // namespace CoreIPC + +namespace WebCore { +class ResourceError; +class ResourceResponse; +} // namespace WebCore + +namespace WebKit { + +class CustomProtocolManager { + WTF_MAKE_NONCOPYABLE(CustomProtocolManager); + +public: + static CustomProtocolManager& shared(); + + void registerScheme(const String&); + void unregisterScheme(const String&); + bool supportsScheme(const String&); + + void didReceiveMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&); + void didFailWithError(uint64_t customProtocolID, const WebCore::ResourceError&); + void didLoadData(uint64_t customProtocolID, const CoreIPC::DataReference&); + void didReceiveResponse(uint64_t customProtocolID, const WebCore::ResourceResponse&, uint32_t cacheStoragePolicy); + void didFinishLoading(uint64_t customProtocolID); + +#if PLATFORM(MAC) + static void registerCustomProtocolClass(); + void addCustomProtocol(WKCustomProtocol *); + void removeCustomProtocol(WKCustomProtocol *); +#endif + +private: + CustomProtocolManager() { } + void didReceiveCustomProtocolManagerMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&); + + HashSet<String> m_registeredSchemes; + +#if PLATFORM(MAC) + typedef HashMap<uint64_t, RetainPtr<WKCustomProtocol> > CustomProtocolMap; + CustomProtocolMap m_customProtocolMap; + WKCustomProtocol *protocolForID(uint64_t customProtocolID); +#endif +}; + +} // namespace WebKit + +#endif // ENABLE(CUSTOM_PROTOCOLS) + +#endif // CustomProtocolManager_h diff --git a/Source/WebKit2/WebProcess/Network/CustomProtocols/CustomProtocolManager.messages.in b/Source/WebKit2/WebProcess/Network/CustomProtocols/CustomProtocolManager.messages.in new file mode 100644 index 000000000..e8efd8389 --- /dev/null +++ b/Source/WebKit2/WebProcess/Network/CustomProtocols/CustomProtocolManager.messages.in @@ -0,0 +1,32 @@ +# Copyright (C) 2012 Apple Inc. All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +#if ENABLE(CUSTOM_PROTOCOLS) + +messages -> CustomProtocolManager { + DidFailWithError(uint64_t customProtocolID, WebCore::ResourceError error) + DidLoadData(uint64_t customProtocolID, CoreIPC::DataReference data) + DidReceiveResponse(uint64_t customProtocolID, WebCore::ResourceResponse response, uint32_t cacheStoragePolicy) + DidFinishLoading(uint64_t customProtocolID) +} + +#endif // ENABLE(CUSTOM_PROTOCOLS) diff --git a/Source/WebKit2/WebProcess/Network/CustomProtocols/mac/CustomProtocolManagerMac.mm b/Source/WebKit2/WebProcess/Network/CustomProtocols/mac/CustomProtocolManagerMac.mm new file mode 100644 index 000000000..0e96003e8 --- /dev/null +++ b/Source/WebKit2/WebProcess/Network/CustomProtocols/mac/CustomProtocolManagerMac.mm @@ -0,0 +1,190 @@ +/* + * Copyright (C) 2012 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "config.h" +#import "CustomProtocolManager.h" + +#if ENABLE(CUSTOM_PROTOCOLS) + +#import "CustomProtocolManagerProxyMessages.h" +#import "DataReference.h" +#import "WebCoreArgumentCoders.h" +#import "WebProcess.h" +#import <WebCore/KURL.h> + +using namespace WebKit; + +static uint64_t generateCustomProtocolID() +{ + static uint64_t uniqueCustomProtocolID = 0; + return ++uniqueCustomProtocolID; +} + +@interface WKCustomProtocol : NSURLProtocol { +@private + uint64_t _customProtocolID; +} +@property (nonatomic, readonly) uint64_t customProtocolID; +@end + +@implementation WKCustomProtocol + +@synthesize customProtocolID = _customProtocolID; + ++ (BOOL)canInitWithRequest:(NSURLRequest *)request +{ + return WebKit::CustomProtocolManager::shared().supportsScheme([[[request URL] scheme] lowercaseString]); +} + ++ (NSURLRequest *)canonicalRequestForRequest:(NSURLRequest *)request +{ + return request; +} + ++ (BOOL)requestIsCacheEquivalent:(NSURLRequest *)a toRequest:(NSURLRequest *)b +{ + return NO; +} + +- (id)initWithRequest:(NSURLRequest *)request cachedResponse:(NSCachedURLResponse *)cachedResponse client:(id<NSURLProtocolClient>)client +{ + self = [super initWithRequest:request cachedResponse:cachedResponse client:client]; + if (!self) + return nil; + + _customProtocolID = generateCustomProtocolID(); + WebKit::CustomProtocolManager::shared().addCustomProtocol(self); + return self; +} + +- (void)startLoading +{ + WebProcess::shared().connection()->send(Messages::CustomProtocolManagerProxy::StartLoading(self.customProtocolID, [self request]), 0); +} + +- (void)stopLoading +{ + WebProcess::shared().connection()->send(Messages::CustomProtocolManagerProxy::StopLoading(self.customProtocolID), 0); + WebKit::CustomProtocolManager::shared().removeCustomProtocol(self); +} + +@end + +namespace WebKit { + +CustomProtocolManager& CustomProtocolManager::shared() +{ + DEFINE_STATIC_LOCAL(CustomProtocolManager, customProtocolManager, ()); + return customProtocolManager; +} + +void CustomProtocolManager::registerCustomProtocolClass() +{ + [NSURLProtocol registerClass:[WKCustomProtocol class]]; +} + +void CustomProtocolManager::addCustomProtocol(WKCustomProtocol *customProtocol) +{ + ASSERT(customProtocol); + m_customProtocolMap.add(customProtocol.customProtocolID, customProtocol); +} + +void CustomProtocolManager::removeCustomProtocol(WKCustomProtocol *customProtocol) +{ + ASSERT(customProtocol); + m_customProtocolMap.remove(customProtocol.customProtocolID); +} + +void CustomProtocolManager::registerScheme(const String& scheme) +{ + m_registeredSchemes.add(scheme); +} + +void CustomProtocolManager::unregisterScheme(const String& scheme) +{ + m_registeredSchemes.remove(scheme); +} + +bool CustomProtocolManager::supportsScheme(const String& scheme) +{ + return m_registeredSchemes.contains(scheme); +} + +void CustomProtocolManager::didReceiveMessage(CoreIPC::Connection* connection, CoreIPC::MessageID messageID, CoreIPC::MessageDecoder& decoder) +{ + didReceiveCustomProtocolManagerMessage(connection, messageID, decoder); +} + +void CustomProtocolManager::didFailWithError(uint64_t customProtocolID, const WebCore::ResourceError& error) +{ + WKCustomProtocol *protocol = protocolForID(customProtocolID); + if (!protocol) + return; + + [[protocol client] URLProtocol:protocol didFailWithError:error.nsError()]; + removeCustomProtocol(protocol); +} + +void CustomProtocolManager::didLoadData(uint64_t customProtocolID, const CoreIPC::DataReference& data) +{ + WKCustomProtocol *protocol = protocolForID(customProtocolID); + if (!protocol) + return; + + [[protocol client] URLProtocol:protocol didLoadData:[NSData dataWithBytes:(void*)data.data() length:data.size()]]; +} + +void CustomProtocolManager::didReceiveResponse(uint64_t customProtocolID, const WebCore::ResourceResponse& response, uint32_t cacheStoragePolicy) +{ + WKCustomProtocol *protocol = protocolForID(customProtocolID); + if (!protocol) + return; + + [[protocol client] URLProtocol:protocol didReceiveResponse:response.nsURLResponse() cacheStoragePolicy:static_cast<NSURLCacheStoragePolicy>(cacheStoragePolicy)]; +} + +void CustomProtocolManager::didFinishLoading(uint64_t customProtocolID) +{ + WKCustomProtocol *protocol = protocolForID(customProtocolID); + if (!protocol) + return; + + [[protocol client] URLProtocolDidFinishLoading:protocol]; + removeCustomProtocol(protocol); +} + +WKCustomProtocol *CustomProtocolManager::protocolForID(uint64_t customProtocolID) +{ + CustomProtocolMap::const_iterator it = m_customProtocolMap.find(customProtocolID); + if (it == m_customProtocolMap.end()) + return nil; + + ASSERT(it->value); + return it->value.get(); +} + +} // namespace WebKit + +#endif // ENABLE(CUSTOM_PROTOCOLS) diff --git a/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.cpp b/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.cpp index 10d672208..9b687ba7c 100644 --- a/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.cpp +++ b/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.cpp @@ -26,10 +26,17 @@ #include "config.h" #include "NetworkProcessConnection.h" +#include "DataReference.h" +#include "NetworkConnectionToWebProcessMessages.h" +#include "WebCoreArgumentCoders.h" #include "WebProcess.h" +#include "WebResourceBuffer.h" +#include <WebCore/ResourceBuffer.h> #if ENABLE(NETWORK_PROCESS) +using namespace WebCore; + namespace WebKit { NetworkProcessConnection::NetworkProcessConnection(CoreIPC::Connection::Identifier connectionIdentifier) @@ -44,15 +51,13 @@ NetworkProcessConnection::~NetworkProcessConnection() void NetworkProcessConnection::didReceiveMessage(CoreIPC::Connection* connection, CoreIPC::MessageID messageID, CoreIPC::MessageDecoder& decoder) { - if (messageID.is<CoreIPC::MessageClassNetworkProcessConnection>()) { - didReceiveNetworkProcessConnectionMessage(connection, messageID, decoder); + if (messageID.is<CoreIPC::MessageClassWebResourceLoader>()) { + if (WebResourceLoader* webResourceLoader = WebProcess::shared().webResourceLoadScheduler().webResourceLoaderForIdentifier(decoder.destinationID())) + webResourceLoader->didReceiveWebResourceLoaderMessage(connection, messageID, decoder); + return; } - ASSERT_NOT_REACHED(); -} -void NetworkProcessConnection::didReceiveSyncMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&, OwnPtr<CoreIPC::MessageEncoder>&) -{ ASSERT_NOT_REACHED(); } @@ -66,11 +71,6 @@ void NetworkProcessConnection::didReceiveInvalidMessage(CoreIPC::Connection*, Co { } -void NetworkProcessConnection::startResourceLoad(ResourceLoadIdentifier resourceLoadIdentifier) -{ - WebProcess::shared().webResourceLoadScheduler().startResourceLoad(resourceLoadIdentifier); -} - } // namespace WebKit #endif // ENABLE(NETWORK_PROCESS) diff --git a/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.h b/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.h index 6d6a98fdd..7de523bda 100644 --- a/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.h +++ b/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.h @@ -32,6 +32,16 @@ #if ENABLE(NETWORK_PROCESS) +namespace CoreIPC { +class DataReference; +} + +namespace WebCore { +class ResourceError; +class ResourceRequest; +class ResourceResponse; +} + namespace WebKit { typedef uint64_t ResourceLoadIdentifier; @@ -51,14 +61,9 @@ private: // CoreIPC::Connection::Client virtual void didReceiveMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&); - virtual void didReceiveSyncMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&, OwnPtr<CoreIPC::MessageEncoder>&); virtual void didClose(CoreIPC::Connection*); virtual void didReceiveInvalidMessage(CoreIPC::Connection*, CoreIPC::StringReference messageReceiverName, CoreIPC::StringReference messageName) OVERRIDE; - void didReceiveNetworkProcessConnectionMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&); - - void startResourceLoad(ResourceLoadIdentifier); - // The connection from the web process to the network process. RefPtr<CoreIPC::Connection> m_connection; }; diff --git a/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.messages.in b/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.messages.in index 69aeabb24..6b375a5e0 100644 --- a/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.messages.in +++ b/Source/WebKit2/WebProcess/Network/NetworkProcessConnection.messages.in @@ -24,9 +24,6 @@ messages -> NetworkProcessConnection { - // FIXME (NetworkProcess): This message is for the NetworkProcess to tell the WebProcess to start a load. - // Once the NetworkProcess is doing the loading itself then we should remove it. - StartResourceLoad(uint64_t resourceLoadIdentifier) } #endif // ENABLE(NETWORK_PROCESS) diff --git a/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.cpp b/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.cpp index def60e45a..28820dd45 100644 --- a/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.cpp +++ b/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.cpp @@ -29,13 +29,17 @@ #include "Logging.h" #include "NetworkConnectionToWebProcessMessages.h" #include "NetworkProcessConnection.h" +#include "NetworkResourceLoadParameters.h" #include "WebCoreArgumentCoders.h" #include "WebProcess.h" +#include "WebResourceLoader.h" #include <WebCore/DocumentLoader.h> #include <WebCore/Frame.h> #include <WebCore/FrameLoader.h> #include <WebCore/NetscapePlugInStreamLoader.h> +#include <WebCore/ResourceBuffer.h> #include <WebCore/ResourceLoader.h> +#include <WebCore/Settings.h> #include <WebCore/SubresourceLoader.h> #include <wtf/text/CString.h> @@ -72,7 +76,7 @@ PassRefPtr<NetscapePlugInStreamLoader> WebResourceLoadScheduler::schedulePluginS void WebResourceLoadScheduler::scheduleLoad(ResourceLoader* resourceLoader, ResourceLoadPriority priority) { - LOG(Network, "(WebProcess) WebResourceLoadScheduler::scheduleLoad, url '%s' priority %i", resourceLoader->url().string().utf8().data(), priority); + LOG(NetworkScheduling, "(WebProcess) WebResourceLoadScheduler::scheduleLoad, url '%s' priority %i", resourceLoader->url().string().utf8().data(), priority); ASSERT(resourceLoader); ASSERT(priority != ResourceLoadPriorityUnresolved); @@ -93,21 +97,29 @@ void WebResourceLoadScheduler::scheduleLoad(ResourceLoader* resourceLoader, Reso DEFINE_STATIC_LOCAL(KURL, dataURL, (KURL(), "data:")); request.setURL(dataURL); } - - if (!WebProcess::shared().networkConnection()->connection()->sendSync(Messages::NetworkConnectionToWebProcess::ScheduleNetworkRequest(request, priority), Messages::NetworkConnectionToWebProcess::ScheduleNetworkRequest::Reply(identifier), 0)) { + + // FIXME (NetworkProcess): When the ResourceLoader asks its FrameLoaderClient about using + // credential storage it passes along its identifier. + // But at this point it doesn't have the correct identifier yet. + // In practice clients we know about don't care about the identifier, but this is another reason + // we need to make sure ResourceLoaders get correct identifiers right off the bat. + StoredCredentials allowStoredCredentials = resourceLoader->shouldUseCredentialStorage() ? AllowStoredCredentials : DoNotAllowStoredCredentials; + + NetworkResourceLoadParameters loadParameters(request, priority, resourceLoader->shouldSniffContent() ? SniffContent : DoNotSniffContent, allowStoredCredentials); + if (!WebProcess::shared().networkConnection()->connection()->sendSync(Messages::NetworkConnectionToWebProcess::ScheduleResourceLoad(loadParameters), Messages::NetworkConnectionToWebProcess::ScheduleResourceLoad::Reply(identifier), 0)) { // FIXME (NetworkProcess): What should we do if this fails? ASSERT_NOT_REACHED(); } resourceLoader->setIdentifier(identifier); - m_pendingResourceLoaders.set(identifier, resourceLoader); + m_webResourceLoaders.set(identifier, WebResourceLoader::create(resourceLoader)); notifyDidScheduleResourceRequest(resourceLoader); } void WebResourceLoadScheduler::addMainResourceLoad(ResourceLoader* resourceLoader) { - LOG(Network, "(WebProcess) WebResourceLoadScheduler::addMainResourceLoad, url '%s'", resourceLoader->url().string().utf8().data()); + LOG(NetworkScheduling, "(WebProcess) WebResourceLoadScheduler::addMainResourceLoad, url '%s'", resourceLoader->url().string().utf8().data()); ResourceLoadIdentifier identifier; @@ -118,13 +130,13 @@ void WebResourceLoadScheduler::addMainResourceLoad(ResourceLoader* resourceLoade resourceLoader->setIdentifier(identifier); - m_activeResourceLoaders.set(identifier, resourceLoader); + m_coreResourceLoaders.set(identifier, resourceLoader); } void WebResourceLoadScheduler::remove(ResourceLoader* resourceLoader) { ASSERT(resourceLoader); - LOG(Network, "(WebProcess) WebResourceLoadScheduler::remove, url '%s'", resourceLoader->url().string().utf8().data()); + LOG(NetworkScheduling, "(WebProcess) WebResourceLoadScheduler::remove, url '%s'", resourceLoader->url().string().utf8().data()); // FIXME (NetworkProcess): It's possible for a resourceLoader to be removed before it ever started, // meaning before it even has an identifier. @@ -137,29 +149,24 @@ void WebResourceLoadScheduler::remove(ResourceLoader* resourceLoader) return; } + // FIXME (NetworkProcess): We should only tell the NetworkProcess to remove load identifiers for ResourceLoaders that were never started. + // If a resource load was actually started within the NetworkProcess then the NetworkProcess handles clearing out the identifier. WebProcess::shared().networkConnection()->connection()->send(Messages::NetworkConnectionToWebProcess::RemoveLoadIdentifier(identifier), 0); - ASSERT(m_pendingResourceLoaders.contains(identifier) || m_activeResourceLoaders.contains(identifier)); - m_pendingResourceLoaders.remove(identifier); - m_activeResourceLoaders.remove(identifier); + ASSERT(m_webResourceLoaders.contains(identifier) || m_coreResourceLoaders.contains(identifier)); + m_webResourceLoaders.remove(identifier); + m_coreResourceLoaders.remove(identifier); } -void WebResourceLoadScheduler::crossOriginRedirectReceived(ResourceLoader* resourceLoader, const KURL& redirectURL) +void WebResourceLoadScheduler::crossOriginRedirectReceived(ResourceLoader*, const KURL&) { - LOG(Network, "(WebProcess) WebResourceLoadScheduler::crossOriginRedirectReceived. From '%s' to '%s'", resourceLoader->url().string().utf8().data(), redirectURL.string().utf8().data()); - - ASSERT(resourceLoader); - ASSERT(resourceLoader->identifier()); - - if (!WebProcess::shared().networkConnection()->connection()->sendSync(Messages::NetworkConnectionToWebProcess::crossOriginRedirectReceived(resourceLoader->identifier(), redirectURL), Messages::NetworkConnectionToWebProcess::crossOriginRedirectReceived::Reply(), 0)) { - // FIXME (NetworkProcess): What should we do if this fails? - ASSERT_NOT_REACHED(); - } + // We handle cross origin redirects entirely within the NetworkProcess. + // We override this call in the WebProcess to make it a no-op. } void WebResourceLoadScheduler::servePendingRequests(ResourceLoadPriority minimumPriority) { - LOG(Network, "(WebProcess) WebResourceLoadScheduler::servePendingRequests"); + LOG(NetworkScheduling, "(WebProcess) WebResourceLoadScheduler::servePendingRequests"); // If this WebProcess has its own request suspension count then we don't even // have to bother messaging the NetworkProcess. @@ -189,25 +196,6 @@ void WebResourceLoadScheduler::setSerialLoadingEnabled(bool enabled) WebProcess::shared().networkConnection()->connection()->sendSync(Messages::NetworkConnectionToWebProcess::SetSerialLoadingEnabled(enabled), Messages::NetworkConnectionToWebProcess::SetSerialLoadingEnabled::Reply(), 0); } -void WebResourceLoadScheduler::startResourceLoad(ResourceLoadIdentifier identifier) -{ - RefPtr<ResourceLoader> loader = m_pendingResourceLoaders.take(identifier); - - // <rdar://problem/12596761> and http://webkit.org/b/100792 - // There is a race condition where the WebProcess might tell the NetworkProcess to remove a resource load identifier - // at the very time the NetworkProcess is telling the WebProcess to start that particular load. - // We'd like to remove that race condition but it makes sense for release builds to do an early return. - ASSERT(loader); - if (!loader) - return; - - LOG(Network, "(WebProcess) WebResourceLoadScheduler::startResourceLoad starting load for '%s'", loader->url().string().utf8().data()); - - m_activeResourceLoaders.set(identifier, loader); - - startResourceLoader(loader.get()); -} - } // namespace WebKit #endif // ENABLE(NETWORK_PROCESS) diff --git a/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.h b/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.h index 422427bc6..d6ca6710a 100644 --- a/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.h +++ b/Source/WebKit2/WebProcess/Network/WebResourceLoadScheduler.h @@ -26,6 +26,7 @@ #ifndef WebResourceLoadScheduler_h #define WebResourceLoadScheduler_h +#include "WebResourceLoader.h" #include <WebCore/ResourceLoadPriority.h> #include <WebCore/ResourceLoadScheduler.h> #include <WebCore/ResourceLoader.h> @@ -57,17 +58,13 @@ public: virtual void setSerialLoadingEnabled(bool) OVERRIDE; + WebResourceLoader* webResourceLoaderForIdentifier(ResourceLoadIdentifier identifier) const { return m_webResourceLoaders.get(identifier).get(); } + private: void scheduleLoad(WebCore::ResourceLoader*, WebCore::ResourceLoadPriority); - - // NetworkProcessConnection gets to tell loads to actually start. - // FIXME (NetworkProcess): Once actual loading takes place in the NetworkProcess we won't need this. - friend class NetworkProcessConnection; - void startResourceLoad(ResourceLoadIdentifier); - typedef HashMap<unsigned long, RefPtr<WebCore::ResourceLoader> > ResourceLoaderMap; - ResourceLoaderMap m_pendingResourceLoaders; - ResourceLoaderMap m_activeResourceLoaders; + HashMap<unsigned long, RefPtr<WebCore::ResourceLoader> > m_coreResourceLoaders; + HashMap<unsigned long, RefPtr<WebResourceLoader> > m_webResourceLoaders; unsigned m_suspendPendingRequestsCount; diff --git a/Source/WebKit2/WebProcess/Network/WebResourceLoader.cpp b/Source/WebKit2/WebProcess/Network/WebResourceLoader.cpp new file mode 100644 index 000000000..0fbd1a5dd --- /dev/null +++ b/Source/WebKit2/WebProcess/Network/WebResourceLoader.cpp @@ -0,0 +1,173 @@ +/* + * Copyright (C) 2012 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include "config.h" +#include "WebResourceLoader.h" + +#if ENABLE(NETWORK_PROCESS) + +#include "DataReference.h" +#include "Logging.h" +#include "NetworkConnectionToWebProcessMessages.h" +#include "NetworkProcessConnection.h" +#include "NetworkResourceLoaderMessages.h" +#include "WebCoreArgumentCoders.h" +#include "WebProcess.h" +#include <WebCore/ResourceLoader.h> + +using namespace WebCore; + +namespace WebKit { + +PassRefPtr<WebResourceLoader> WebResourceLoader::create(PassRefPtr<ResourceLoader> coreLoader) +{ + return adoptRef(new WebResourceLoader(coreLoader)); +} + +WebResourceLoader::WebResourceLoader(PassRefPtr<WebCore::ResourceLoader> coreLoader) + : m_coreLoader(coreLoader) +{ +} + +WebResourceLoader::~WebResourceLoader() +{ +} + +CoreIPC::Connection* WebResourceLoader::connection() const +{ + return WebProcess::shared().networkConnection()->connection(); +} + +uint64_t WebResourceLoader::destinationID() const +{ + return m_coreLoader->identifier(); +} + +void WebResourceLoader::willSendRequest(uint64_t requestID, const ResourceRequest& proposedRequest, const ResourceResponse& redirectResponse) +{ + LOG(Network, "(WebProcess) WebResourceLoader::willSendRequest to '%s'", proposedRequest.url().string().utf8().data()); + + ResourceRequest newRequest = proposedRequest; + m_coreLoader->willSendRequest(newRequest, redirectResponse); + + send(Messages::NetworkResourceLoader::WillSendRequestHandled(requestID, newRequest)); +} + +void WebResourceLoader::didReceiveResponse(const WebCore::ResourceResponse& response) +{ + LOG(Network, "(WebProcess) WebResourceLoader::didReceiveResponse for '%s'", m_coreLoader->url().string().utf8().data()); + m_coreLoader->didReceiveResponse(response); +} + +void WebResourceLoader::didReceiveData(const CoreIPC::DataReference& data, int64_t encodedDataLength, bool allAtOnce) +{ + LOG(Network, "(WebProcess) WebResourceLoader::didReceiveData of size %i for '%s'", (int)data.size(), m_coreLoader->url().string().utf8().data()); + m_coreLoader->didReceiveData(reinterpret_cast<const char*>(data.data()), data.size(), encodedDataLength, allAtOnce); +} + +void WebResourceLoader::didFinishResourceLoad(double finishTime) +{ + LOG(Network, "(WebProcess) WebResourceLoader::didFinishResourceLoad for '%s'", m_coreLoader->url().string().utf8().data()); + m_coreLoader->didFinishLoading(finishTime); +} + +void WebResourceLoader::didFailResourceLoad(const ResourceError& error) +{ + LOG(Network, "(WebProcess) WebResourceLoader::didFailResourceLoad for '%s'", m_coreLoader->url().string().utf8().data()); + + m_coreLoader->didFail(error); +} + +void WebResourceLoader::didReceiveResource(const ShareableResource::Handle& handle, double finishTime) +{ + LOG(Network, "(WebProcess) WebResourceLoader::didReceiveResource for '%s'", m_coreLoader->url().string().utf8().data()); + + RefPtr<ShareableResource> resource = ShareableResource::create(handle); + + // Only send data to the didReceiveData callback if it exists. + if (!resource->size()) { + // FIXME (NetworkProcess): Give ResourceLoader the ability to take ResourceBuffer arguments. + // That will allow us to pass it along to CachedResources and allow them to hang on to the shared memory behind the scenes. + // FIXME (NetworkProcess): Pass along the correct value for encodedDataLength. + m_coreLoader->didReceiveData(reinterpret_cast<const char*>(resource->data()), resource->size(), -1 /* encodedDataLength */ , true); + } + + m_coreLoader->didFinishLoading(finishTime); +} + +void WebResourceLoader::canAuthenticateAgainstProtectionSpace(uint64_t requestID, const ProtectionSpace& protectionSpace) +{ + send(Messages::NetworkResourceLoader::CanAuthenticateAgainstProtectionSpaceHandled(requestID, m_coreLoader->canAuthenticateAgainstProtectionSpace(protectionSpace))); +} + +void WebResourceLoader::didReceiveAuthenticationChallenge(const AuthenticationChallenge& challenge) +{ + LOG(Network, "(WebProcess) WebResourceLoader::didReceiveAuthenticationChallenge for '%s'", m_coreLoader->url().string().utf8().data()); + + m_currentAuthenticationChallenge = adoptPtr(new AuthenticationChallenge(challenge)); + m_currentAuthenticationChallenge->setAuthenticationClient(this); + + m_coreLoader->didReceiveAuthenticationChallenge(*m_currentAuthenticationChallenge); +} + +void WebResourceLoader::didCancelAuthenticationChallenge(const AuthenticationChallenge& challenge) +{ + if (m_currentAuthenticationChallenge->identifier() != challenge.identifier()) + return; + + LOG(Network, "(WebProcess) WebResourceLoader::didCancelAuthenticationChallenge for '%s'", m_coreLoader->url().string().utf8().data()); + + m_coreLoader->didCancelAuthenticationChallenge(*m_currentAuthenticationChallenge); + m_currentAuthenticationChallenge.clear(); +} + +// WebCore::AuthenticationClient +void WebResourceLoader::receivedCredential(const AuthenticationChallenge& challenge, const Credential& credential) +{ + ASSERT(m_currentAuthenticationChallenge && challenge == *m_currentAuthenticationChallenge); + send(Messages::NetworkResourceLoader::ReceivedAuthenticationCredential(challenge, credential)); + + m_currentAuthenticationChallenge.clear(); +} + +void WebResourceLoader::receivedRequestToContinueWithoutCredential(const AuthenticationChallenge& challenge) +{ + ASSERT(m_currentAuthenticationChallenge && challenge == *m_currentAuthenticationChallenge); + send(Messages::NetworkResourceLoader::ReceivedRequestToContinueWithoutAuthenticationCredential(challenge)); + + m_currentAuthenticationChallenge.clear(); +} + +void WebResourceLoader::receivedCancellation(const AuthenticationChallenge& challenge) +{ + ASSERT(m_currentAuthenticationChallenge && challenge == *m_currentAuthenticationChallenge); + send(Messages::NetworkResourceLoader::ReceivedAuthenticationCancellation(challenge)); + + m_currentAuthenticationChallenge.clear(); +} + +} // namespace WebKit + +#endif // ENABLE(NETWORK_PROCESS) diff --git a/Source/WebKit2/WebProcess/Network/WebResourceLoader.h b/Source/WebKit2/WebProcess/Network/WebResourceLoader.h new file mode 100644 index 000000000..fa3783cb9 --- /dev/null +++ b/Source/WebKit2/WebProcess/Network/WebResourceLoader.h @@ -0,0 +1,101 @@ +/* + * Copyright (C) 2012 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef WebResourceLoader_h +#define WebResourceLoader_h + +#if ENABLE(NETWORK_PROCESS) + +#include "Connection.h" +#include "MessageSender.h" +#include "ShareableResource.h" +#include <WebCore/AuthenticationClient.h> +#include <wtf/PassRefPtr.h> +#include <wtf/RefCounted.h> +#include <wtf/RefPtr.h> + +namespace CoreIPC { +class DataReference; +} + +namespace WebCore { +class AuthenticationChallenge; +class ProtectionSpace; +class ResourceBuffer; +class ResourceError; +class ResourceLoader; +class ResourceRequest; +class ResourceResponse; +} + +namespace WebKit { + +typedef uint64_t ResourceLoadIdentifier; + +class WebResourceLoader : public RefCounted<WebResourceLoader>, public CoreIPC::MessageSender<WebResourceLoader>, public WebCore::AuthenticationClient { +public: + static PassRefPtr<WebResourceLoader> create(PassRefPtr<WebCore::ResourceLoader>); + + ~WebResourceLoader(); + + // Used by MessageSender. + CoreIPC::Connection* connection() const; + uint64_t destinationID() const; + + void didReceiveWebResourceLoaderMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&); + + using RefCounted<WebResourceLoader>::ref; + using RefCounted<WebResourceLoader>::deref; + + virtual void receivedCredential(const WebCore::AuthenticationChallenge&, const WebCore::Credential&); + virtual void receivedRequestToContinueWithoutCredential(const WebCore::AuthenticationChallenge&); + virtual void receivedCancellation(const WebCore::AuthenticationChallenge&); + +private: + WebResourceLoader(PassRefPtr<WebCore::ResourceLoader>); + + void willSendRequest(uint64_t requestID, const WebCore::ResourceRequest&, const WebCore::ResourceResponse& redirectResponse); + void didReceiveResponse(const WebCore::ResourceResponse&); + void didReceiveData(const CoreIPC::DataReference&, int64_t encodedDataLength, bool allAtOnce); + void didFinishResourceLoad(double finishTime); + void didFailResourceLoad(const WebCore::ResourceError&); + void didReceiveResource(const ShareableResource::Handle&, double finishTime); + + void canAuthenticateAgainstProtectionSpace(uint64_t requestID, const WebCore::ProtectionSpace&); + void didReceiveAuthenticationChallenge(const WebCore::AuthenticationChallenge&); + void didCancelAuthenticationChallenge(const WebCore::AuthenticationChallenge&); + + virtual void refAuthenticationClient() { ref(); } + virtual void derefAuthenticationClient() { deref(); } + + RefPtr<WebCore::ResourceLoader> m_coreLoader; + OwnPtr<WebCore::AuthenticationChallenge> m_currentAuthenticationChallenge; +}; + +} // namespace WebKit + +#endif // ENABLE(NETWORK_PROCESS) + +#endif // WebResourceLoader_h diff --git a/Source/WebKit2/WebProcess/Network/WebResourceLoader.messages.in b/Source/WebKit2/WebProcess/Network/WebResourceLoader.messages.in new file mode 100644 index 000000000..96b30b0ed --- /dev/null +++ b/Source/WebKit2/WebProcess/Network/WebResourceLoader.messages.in @@ -0,0 +1,38 @@ +# Copyright (C) 2012 Apple Inc. All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +messages -> WebResourceLoader { + + // FIXME (NetworkProcess): We'll need much more granularity for response messages. + WillSendRequest(uint64_t requestID, WebCore::ResourceRequest request, WebCore::ResourceResponse redirectResponse) + DidReceiveResponse(WebCore::ResourceResponse response) + DidReceiveData(CoreIPC::DataReference data, int64_t encodedDataLength, bool allAtOnce) + DidFinishResourceLoad(double finishTime) + DidFailResourceLoad(WebCore::ResourceError error) + + CanAuthenticateAgainstProtectionSpace(uint64_t requestID, WebCore::ProtectionSpace protectionSpace) + DidReceiveAuthenticationChallenge(WebCore::AuthenticationChallenge challenge) + DidCancelAuthenticationChallenge(WebCore::AuthenticationChallenge challenge) + + // DidReceiveResource is for when we have the entire resource data available at once, such as when the resource is cached in memory + DidReceiveResource(WebKit::ShareableResource::Handle resource, double finishTime) +} diff --git a/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.cpp b/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.cpp index 3b9c6125b..f1e0e5b10 100644 --- a/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.cpp +++ b/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.cpp @@ -920,7 +920,12 @@ bool NetscapePlugin::isEditingCommandEnabled(const String& /* commandName */) { return false; } - + +bool NetscapePlugin::shouldAllowScripting() +{ + return true; +} + bool NetscapePlugin::handlesPageScaleFactor() { return false; diff --git a/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.h b/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.h index 1f6168aad..559aadab5 100644 --- a/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.h +++ b/Source/WebKit2/WebProcess/Plugins/Netscape/NetscapePlugin.h @@ -206,6 +206,8 @@ private: virtual bool handleEditingCommand(const String& commandName, const String& argument) OVERRIDE; virtual bool isEditingCommandEnabled(const String&) OVERRIDE; + + virtual bool shouldAllowScripting() OVERRIDE; virtual bool handlesPageScaleFactor() OVERRIDE; diff --git a/Source/WebKit2/WebProcess/Plugins/PDF/PDFLayerControllerDetails.h b/Source/WebKit2/WebProcess/Plugins/PDF/PDFLayerControllerDetails.h index 6e7b52af2..f387ded4e 100644 --- a/Source/WebKit2/WebProcess/Plugins/PDF/PDFLayerControllerDetails.h +++ b/Source/WebKit2/WebProcess/Plugins/PDF/PDFLayerControllerDetails.h @@ -35,6 +35,8 @@ - (void)saveToPDF; - (void)pdfLayerController:(PDFLayerController *)pdfLayerController didChangeActiveAnnotation:(PDFAnnotation *)annotation; +- (void)pdfLayerController:(PDFLayerController *)pdfLayerController clickedLinkWithURL:(NSURL *)url; +- (void)pdfLayerController:(PDFLayerController *)pdfLayerController didChangeContentScaleFactor:(CGFloat)scaleFactor; @end @@ -52,8 +54,11 @@ - (void)setDisplayMode:(int)mode; - (void)setDisplaysPageBreaks:(BOOL)pageBreaks; -- (CGFloat)tileScaleFactor; -- (void)setTileScaleFactor:(CGFloat)scaleFactor; +- (CGFloat)contentScaleFactor; +- (void)setContentScaleFactor:(CGFloat)scaleFactor; + +- (CGFloat)deviceScaleFactor; +- (void)setDeviceScaleFactor:(CGFloat)scaleFactor; - (CGSize)contentSize; - (CGSize)contentSizeRespectingZoom; @@ -67,12 +72,15 @@ - (void)scrollWithDelta:(CGSize)delta; - (void)mouseDown:(NSEvent *)event; +- (void)rightMouseDown:(NSEvent *)event; - (void)mouseMoved:(NSEvent *)event; - (void)mouseUp:(NSEvent *)event; - (void)mouseDragged:(NSEvent *)event; - (void)mouseEntered:(NSEvent *)event; - (void)mouseExited:(NSEvent *)event; +- (NSMenu *)menuForEvent:(NSEvent *)event; + - (NSArray *)findString:(NSString *)string caseSensitive:(BOOL)isCaseSensitive highlightMatches:(BOOL)shouldHighlightMatches; - (id)currentSelection; diff --git a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.h b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.h index d3641b66b..a1233fabe 100644 --- a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.h +++ b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.h @@ -30,6 +30,7 @@ #include "Plugin.h" #include "SimplePDFPlugin.h" +#include "WebEvent.h" #include <WebCore/AffineTransform.h> #include <WebCore/ScrollableArea.h> #include <wtf/RetainPtr.h> @@ -62,6 +63,10 @@ public: void setActiveAnnotation(PDFAnnotation *); using ScrollableArea::notifyScrollPositionChanged; + void notifyContentScaleFactorChanged(CGFloat scaleFactor); + + void clickedLink(NSURL *); + void saveToPDF(); private: explicit PDFPlugin(WebFrame*); @@ -77,7 +82,9 @@ private: virtual PassRefPtr<ShareableBitmap> snapshot() OVERRIDE; virtual PlatformLayer* pluginLayer() OVERRIDE; virtual void geometryDidChange(const WebCore::IntSize& pluginSize, const WebCore::IntRect& clipRect, const WebCore::AffineTransform& pluginToRootViewTransform) OVERRIDE; + virtual void contentsScaleFactorChanged(float) OVERRIDE; virtual bool handleMouseEvent(const WebMouseEvent&) OVERRIDE; + virtual bool handleContextMenuEvent(const WebMouseEvent&) OVERRIDE; virtual bool handleKeyboardEvent(const WebKeyboardEvent&) OVERRIDE; virtual bool handleEditingCommand(const String& commandName, const String& argument) OVERRIDE; virtual bool isEditingCommandEnabled(const String&) OVERRIDE; @@ -87,7 +94,9 @@ private: virtual void setScrollOffset(const WebCore::IntPoint&) OVERRIDE; virtual void invalidateScrollbarRect(WebCore::Scrollbar*, const WebCore::IntRect&) OVERRIDE; virtual void invalidateScrollCornerRect(const WebCore::IntRect&) OVERRIDE; - + + NSEvent *nsEventForWebMouseEvent(const WebMouseEvent&); + bool supportsForms(); RetainPtr<CALayer> m_containerLayer; @@ -102,6 +111,7 @@ private: WebCore::AffineTransform m_rootViewToPluginTransform; WebCore::IntPoint m_lastMousePoint; + WebMouseEvent m_lastMouseEvent; RetainPtr<WKPDFLayerControllerDelegate> m_pdfLayerControllerDelegate; }; diff --git a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.mm b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.mm index b09c80b6c..716b24e15 100644 --- a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.mm +++ b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPlugin.mm @@ -28,6 +28,8 @@ #import "config.h" #import "PDFPlugin.h" +#import "ArgumentCoders.h" +#import "DataReference.h" #import "PDFKitImports.h" #import "PDFLayerControllerDetails.h" #import "PDFPluginAnnotation.h" @@ -35,6 +37,8 @@ #import "ShareableBitmap.h" #import "WebEvent.h" #import "WebEventConversion.h" +#import "WebPage.h" +#import "WebPageProxyMessages.h" #import <PDFKit/PDFKit.h> #import <QuartzCore/QuartzCore.h> #import <WebCore/ArchiveResource.h> @@ -43,18 +47,23 @@ #import <WebCore/Chrome.h> #import <WebCore/DocumentLoader.h> #import <WebCore/FocusController.h> +#import <WebCore/FormState.h> #import <WebCore/Frame.h> +#import <WebCore/FrameLoadRequest.h> #import <WebCore/FrameView.h> #import <WebCore/GraphicsContext.h> #import <WebCore/HTMLElement.h> +#import <WebCore/HTMLFormElement.h> #import <WebCore/HTTPHeaderMap.h> #import <WebCore/LocalizedStrings.h> +#import <WebCore/MouseEvent.h> #import <WebCore/Page.h> #import <WebCore/Pasteboard.h> #import <WebCore/PluginData.h> #import <WebCore/RenderBoxModelObject.h> #import <WebCore/ScrollAnimator.h> #import <WebCore/ScrollbarTheme.h> +#import <WebKitSystemInterface.h> using namespace WebCore; @@ -172,7 +181,12 @@ static const char* annotationStyle = - (void)saveToPDF { - // FIXME: Implement. + _pdfPlugin->saveToPDF(); +} + +- (void)pdfLayerController:(PDFLayerController *)pdfLayerController clickedLinkWithURL:(NSURL *)url +{ + _pdfPlugin->clickedLink(url); } - (void)pdfLayerController:(PDFLayerController *)pdfLayerController didChangeActiveAnnotation:(PDFAnnotation *)annotation @@ -180,6 +194,11 @@ static const char* annotationStyle = _pdfPlugin->setActiveAnnotation(annotation); } +- (void)pdfLayerController:(PDFLayerController *)pdfLayerController didChangeContentScaleFactor:(CGFloat)scaleFactor +{ + _pdfPlugin->notifyContentScaleFactorChanged(scaleFactor); +} + @end namespace WebKit { @@ -283,20 +302,25 @@ void PDFPlugin::pdfDocumentDidLoad() [m_pdfLayerController.get() setFrameSize:size()]; m_pdfLayerController.get().document = document.get(); + + [m_pdfLayerController.get() setDeviceScaleFactor:controller()->contentsScaleFactor()]; if (handlesPageScaleFactor()) - pluginView()->setPageScaleFactor([m_pdfLayerController.get() tileScaleFactor], IntPoint()); + pluginView()->setPageScaleFactor([m_pdfLayerController.get() contentScaleFactor], IntPoint()); notifyScrollPositionChanged(IntPoint([m_pdfLayerController.get() scrollPosition])); calculateSizes(); updateScrollbars(); - controller()->invalidate(IntRect(IntPoint(), size())); - runScriptsInPDFDocument(); } +void PDFPlugin::contentsScaleFactorChanged(float contentsScaleFactor) +{ + [m_pdfLayerController.get() setDeviceScaleFactor:contentsScaleFactor]; +} + void PDFPlugin::calculateSizes() { // FIXME: This should come straight from PDFKit. @@ -308,7 +332,7 @@ void PDFPlugin::calculateSizes() void PDFPlugin::destroy() { m_pdfLayerController.get().delegate = 0; - + if (webFrame()) { if (FrameView* frameView = webFrame()->coreFrame()->view()) frameView->removeScrollableArea(this); @@ -360,14 +384,15 @@ PassRefPtr<ShareableBitmap> PDFPlugin::snapshot() { if (size().isEmpty()) return 0; - - // FIXME: Support non-1 page/deviceScaleFactor. + + float contentsScaleFactor = controller()->contentsScaleFactor(); IntSize backingStoreSize = size(); + backingStoreSize.scale(contentsScaleFactor); RefPtr<ShareableBitmap> bitmap = ShareableBitmap::createShareable(backingStoreSize, ShareableBitmap::SupportsAlpha); OwnPtr<GraphicsContext> context = bitmap->createGraphicsContext(); - context->scale(FloatSize(1, -1)); + context->scale(FloatSize(contentsScaleFactor, -contentsScaleFactor)); context->translate(0, -size().height()); [m_pdfLayerController.get() snapshotInContext:context->platformContext()]; @@ -382,7 +407,7 @@ PlatformLayer* PDFPlugin::pluginLayer() void PDFPlugin::geometryDidChange(const IntSize& pluginSize, const IntRect&, const AffineTransform& pluginToRootViewTransform) { - if (size() == pluginSize && pluginView()->pageScaleFactor() == [m_pdfLayerController.get() tileScaleFactor]) + if (size() == pluginSize && pluginView()->pageScaleFactor() == [m_pdfLayerController.get() contentScaleFactor]) return; setSize(pluginSize); @@ -395,11 +420,11 @@ void PDFPlugin::geometryDidChange(const IntSize& pluginSize, const IntRect&, con transform = CATransform3DTranslate(transform, 0, -pluginSize.height(), 0); if (handlesPageScaleFactor()) { - CGFloat magnification = pluginView()->pageScaleFactor() - [m_pdfLayerController.get() tileScaleFactor]; + CGFloat magnification = pluginView()->pageScaleFactor() - [m_pdfLayerController.get() contentScaleFactor]; // FIXME: Instead of m_lastMousePoint, we should use the zoom origin from PluginView::setPageScaleFactor. if (magnification) - [m_pdfLayerController.get() magnifyWithMagnification:magnification atPoint:m_lastMousePoint immediately:YES]; + [m_pdfLayerController.get() magnifyWithMagnification:magnification atPoint:m_lastMousePoint immediately:NO]; } calculateSizes(); @@ -420,7 +445,7 @@ static NSUInteger modifierFlagsFromWebEvent(const WebEvent& event) | (event.metaKey() ? NSCommandKeyMask : 0); } -static NSEventType eventTypeFromWebEvent(const WebEvent& event, bool mouseButtonIsDown) +static NSEventType eventTypeFromWebEvent(const WebEvent& event) { switch (event.type()) { case WebEvent::KeyDown: @@ -449,80 +474,118 @@ static NSEventType eventTypeFromWebEvent(const WebEvent& event, bool mouseButton } break; case WebEvent::MouseMove: - if (mouseButtonIsDown) { - switch (static_cast<const WebMouseEvent&>(event).button()) { - case WebMouseEvent::LeftButton: - return NSLeftMouseDragged; - case WebMouseEvent::RightButton: - return NSRightMouseDragged; - default: - return 0; - } - } else + switch (static_cast<const WebMouseEvent&>(event).button()) { + case WebMouseEvent::LeftButton: + return NSLeftMouseDragged; + case WebMouseEvent::RightButton: + return NSRightMouseDragged; + case WebMouseEvent::NoButton: return NSMouseMoved; + default: + return 0; + } break; default: return 0; } } - -bool PDFPlugin::handleMouseEvent(const WebMouseEvent& event) + +NSEvent *PDFPlugin::nsEventForWebMouseEvent(const WebMouseEvent& event) { - static bool mouseButtonIsDown; - IntPoint mousePosition = event.position(); - // FIXME: Forward mouse events to the appropriate scrollbar. - if (IntRect(m_verticalScrollbarLayer.get().frame).contains(mousePosition) - || IntRect(m_horizontalScrollbarLayer.get().frame).contains(mousePosition) - || IntRect(m_scrollCornerLayer.get().frame).contains(mousePosition)) - return false; - IntPoint positionInPDFView(mousePosition); positionInPDFView = m_rootViewToPluginTransform.mapPoint(positionInPDFView); positionInPDFView.setY(size().height() - positionInPDFView.y()); - + m_lastMousePoint = positionInPDFView; - NSEventType eventType = eventTypeFromWebEvent(event, mouseButtonIsDown); + NSEventType eventType = eventTypeFromWebEvent(event); if (!eventType) - return false; + return 0; NSUInteger modifierFlags = modifierFlagsFromWebEvent(event); - NSEvent *fakeEvent = [NSEvent mouseEventWithType:eventType location:positionInPDFView modifierFlags:modifierFlags timestamp:0 windowNumber:0 context:nil eventNumber:0 clickCount:event.clickCount() pressure:0]; + return [NSEvent mouseEventWithType:eventType location:positionInPDFView modifierFlags:modifierFlags timestamp:0 windowNumber:0 context:nil eventNumber:0 clickCount:event.clickCount() pressure:0]; +} + +bool PDFPlugin::handleMouseEvent(const WebMouseEvent& event) +{ + m_lastMouseEvent = event; + + IntPoint mousePosition = event.position(); + + // FIXME: Forward mouse events to the appropriate scrollbar. + if (IntRect(m_verticalScrollbarLayer.get().frame).contains(mousePosition) + || IntRect(m_horizontalScrollbarLayer.get().frame).contains(mousePosition) + || IntRect(m_scrollCornerLayer.get().frame).contains(mousePosition)) + return false; + + NSEvent *nsEvent = nsEventForWebMouseEvent(event); switch (event.type()) { case WebEvent::MouseMove: - if (mouseButtonIsDown) - [m_pdfLayerController.get() mouseDragged:fakeEvent]; - else - [m_pdfLayerController.get() mouseMoved:fakeEvent]; mouseMovedInContentArea(); - return true; - case WebEvent::MouseDown: { - mouseButtonIsDown = true; - [m_pdfLayerController.get() mouseDown:fakeEvent]; - return true; - } - case WebEvent::MouseUp: { - [m_pdfLayerController.get() mouseUp:fakeEvent]; - mouseButtonIsDown = false; - PlatformMouseEvent platformEvent = platform(event); - return true; - } + + switch (event.button()) { + case WebMouseEvent::LeftButton: + [m_pdfLayerController.get() mouseDragged:nsEvent]; + return true; + case WebMouseEvent::RightButton: + case WebMouseEvent::MiddleButton: + return false; + case WebMouseEvent::NoButton: + [m_pdfLayerController.get() mouseMoved:nsEvent]; + return true; + } + case WebEvent::MouseDown: + switch (event.button()) { + case WebMouseEvent::LeftButton: + [m_pdfLayerController.get() mouseDown:nsEvent]; + return true; + case WebMouseEvent::RightButton: + [m_pdfLayerController.get() rightMouseDown:nsEvent]; + return true; + case WebMouseEvent::MiddleButton: + case WebMouseEvent::NoButton: + return false; + } + case WebEvent::MouseUp: + switch (event.button()) { + case WebMouseEvent::LeftButton: + [m_pdfLayerController.get() mouseUp:nsEvent]; + return true; + case WebMouseEvent::RightButton: + case WebMouseEvent::MiddleButton: + case WebMouseEvent::NoButton: + return false; + } default: break; } - + + return false; +} + +bool PDFPlugin::handleContextMenuEvent(const WebMouseEvent& event) +{ + NSMenu *nsMenu = [m_pdfLayerController.get() menuForEvent:nsEventForWebMouseEvent(event)]; + + FrameView* frameView = webFrame()->coreFrame()->view(); + IntPoint point = frameView->contentsToScreen(IntRect(event.position(), IntSize())).location(); + if (nsMenu) { + WKPopupContextMenu(nsMenu, point); + return true; + } + return false; } bool PDFPlugin::handleKeyboardEvent(const WebKeyboardEvent& event) { - NSEventType eventType = eventTypeFromWebEvent(event, false); + NSEventType eventType = eventTypeFromWebEvent(event); NSUInteger modifierFlags = modifierFlagsFromWebEvent(event); NSEvent *fakeEvent = [NSEvent keyEventWithType:eventType location:NSZeroPoint modifierFlags:modifierFlags timestamp:0 windowNumber:0 context:0 characters:event.text() charactersIgnoringModifiers:event.unmodifiedText() isARepeat:event.isAutoRepeat() keyCode:event.nativeVirtualKeyCode()]; @@ -560,7 +623,7 @@ bool PDFPlugin::isEditingCommandEnabled(const String& commandName) void PDFPlugin::setScrollOffset(const IntPoint& offset) { - SimplePDFPlugin::setScrollOffset(offset); + m_scrollOffset = IntSize(offset.x(), offset.y()); [CATransaction begin]; [m_pdfLayerController.get() setScrollPosition:offset]; @@ -589,6 +652,17 @@ bool PDFPlugin::handlesPageScaleFactor() return webFrame()->isMainFrame(); } +void PDFPlugin::clickedLink(NSURL *url) +{ + Frame* frame = webFrame()->coreFrame(); + + RefPtr<Event> coreEvent; + if (m_lastMouseEvent.type() != WebEvent::NoType) + coreEvent = MouseEvent::create(eventNames().clickEvent, frame->document()->defaultView(), platform(m_lastMouseEvent), 0, 0); + + frame->loader()->urlSelected(url, emptyString(), coreEvent.get(), false, false, MaybeSendReferrer); +} + void PDFPlugin::setActiveAnnotation(PDFAnnotation *annotation) { if (!supportsForms()) @@ -610,6 +684,24 @@ bool PDFPlugin::supportsForms() return webFrame()->isMainFrame(); } +void PDFPlugin::notifyContentScaleFactorChanged(CGFloat scaleFactor) +{ + if (handlesPageScaleFactor()) + pluginView()->setPageScaleFactor(scaleFactor, IntPoint()); + + calculateSizes(); + updateScrollbars(); +} + +void PDFPlugin::saveToPDF() +{ + RetainPtr<CFMutableDataRef> cfData = data(); + + CoreIPC::DataReference dataReference(CFDataGetBytePtr(cfData.get()), CFDataGetLength(cfData.get())); + + webFrame()->page()->send(Messages::WebPageProxy::SavePDFToFileInDownloadsFolder(suggestedFilename(), webFrame()->url(), dataReference)); +} + } // namespace WebKit #endif // ENABLE(PDFKIT_PLUGIN) diff --git a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginChoiceAnnotation.mm b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginChoiceAnnotation.mm index fe996967e..c367eff7f 100644 --- a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginChoiceAnnotation.mm +++ b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginChoiceAnnotation.mm @@ -56,7 +56,7 @@ void PDFPluginChoiceAnnotation::updateGeometry() PDFPluginAnnotation::updateGeometry(); StyledElement* styledElement = static_cast<StyledElement*>(element()); - styledElement->setInlineStyleProperty(CSSPropertyFontSize, choiceAnnotation().font.pointSize * pdfLayerController().tileScaleFactor, CSSPrimitiveValue::CSS_PX); + styledElement->setInlineStyleProperty(CSSPropertyFontSize, choiceAnnotation().font.pointSize * pdfLayerController().contentScaleFactor, CSSPrimitiveValue::CSS_PX); } void PDFPluginChoiceAnnotation::commit() diff --git a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginTextAnnotation.mm b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginTextAnnotation.mm index c94ea15f6..b5df3732d 100644 --- a/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginTextAnnotation.mm +++ b/Source/WebKit2/WebProcess/Plugins/PDF/PDFPluginTextAnnotation.mm @@ -107,7 +107,7 @@ void PDFPluginTextAnnotation::updateGeometry() PDFPluginAnnotation::updateGeometry(); StyledElement* styledElement = static_cast<StyledElement*>(element()); - styledElement->setInlineStyleProperty(CSSPropertyFontSize, textAnnotation().font.pointSize * pdfLayerController().tileScaleFactor, CSSPrimitiveValue::CSS_PX); + styledElement->setInlineStyleProperty(CSSPropertyFontSize, textAnnotation().font.pointSize * pdfLayerController().contentScaleFactor, CSSPrimitiveValue::CSS_PX); } void PDFPluginTextAnnotation::commit() diff --git a/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.h b/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.h index 6b8a93e04..94e1aae14 100644 --- a/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.h +++ b/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.h @@ -66,6 +66,8 @@ protected: WebCore::IntSize pdfDocumentSize() const { return m_pdfDocumentSize; } void setPDFDocumentSize(WebCore::IntSize size) { m_pdfDocumentSize = size; } + + const String& suggestedFilename() { return m_suggestedFilename; } RetainPtr<CFMutableDataRef> data() const { return m_data; } @@ -168,7 +170,11 @@ protected: virtual bool isEditingCommandEnabled(const String&) OVERRIDE; virtual bool handleEditingCommand(const String&, const String&) OVERRIDE; virtual bool handlesPageScaleFactor() OVERRIDE; - + + virtual bool shouldAllowScripting() OVERRIDE { return false; } + + WebCore::IntSize m_scrollOffset; + private: JSObjectRef makeJSPDFDoc(JSContextRef); @@ -189,8 +195,6 @@ private: RefPtr<WebCore::Scrollbar> m_verticalScrollbar; WebFrame* m_frame; - - WebCore::IntSize m_scrollOffset; }; } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.mm b/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.mm index 98a73b2b1..32032c2d8 100644 --- a/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.mm +++ b/Source/WebKit2/WebProcess/Plugins/PDF/SimplePDFPlugin.mm @@ -176,7 +176,7 @@ PluginInfo SimplePDFPlugin::pluginInfo() info.name = builtInPDFPluginName(); MimeClassInfo mimeClassInfo; - mimeClassInfo.type ="application/pdf"; + mimeClassInfo.type = "application/pdf"; mimeClassInfo.desc = pdfDocumentTypeDescription(); mimeClassInfo.extensions.append("pdf"); diff --git a/Source/WebKit2/WebProcess/Plugins/Plugin.h b/Source/WebKit2/WebProcess/Plugins/Plugin.h index ded53d157..54f8b3ad8 100644 --- a/Source/WebKit2/WebProcess/Plugins/Plugin.h +++ b/Source/WebKit2/WebProcess/Plugins/Plugin.h @@ -193,6 +193,9 @@ public: // Ask the plug-in whether it will be able to handle the given editing command. virtual bool isEditingCommandEnabled(const String&) = 0; + + // Ask the plug-in whether it should be allowed to execute JavaScript or navigate to JavaScript URLs. + virtual bool shouldAllowScripting() = 0; // Ask the plug-in whether it wants to override full-page zoom. virtual bool handlesPageScaleFactor() = 0; diff --git a/Source/WebKit2/WebProcess/Plugins/PluginProxy.h b/Source/WebKit2/WebProcess/Plugins/PluginProxy.h index 8104af204..b1a893bdd 100644 --- a/Source/WebKit2/WebProcess/Plugins/PluginProxy.h +++ b/Source/WebKit2/WebProcess/Plugins/PluginProxy.h @@ -103,6 +103,7 @@ private: virtual void setFocus(bool); virtual bool handleEditingCommand(const String& commandName, const String& argument) OVERRIDE; virtual bool isEditingCommandEnabled(const String& commandName) OVERRIDE; + virtual bool shouldAllowScripting() OVERRIDE { return true; } virtual bool handlesPageScaleFactor(); diff --git a/Source/WebKit2/WebProcess/Plugins/PluginView.cpp b/Source/WebKit2/WebProcess/Plugins/PluginView.cpp index e82704105..44f575ad5 100644 --- a/Source/WebKit2/WebProcess/Plugins/PluginView.cpp +++ b/Source/WebKit2/WebProcess/Plugins/PluginView.cpp @@ -68,7 +68,7 @@ using namespace WebCore; namespace WebKit { -static const double pluginSnapshotTimerDelay = 3; +static const double pluginSnapshotTimerDelay = 1; class PluginView::URLRequest : public RefCounted<URLRequest> { public: @@ -784,6 +784,11 @@ bool PluginView::isEditingCommandEnabled(const String& commandName) return m_plugin->isEditingCommandEnabled(commandName); } +bool PluginView::shouldAllowScripting() +{ + return m_plugin->shouldAllowScripting(); +} + void PluginView::notifyWidget(WidgetNotification notification) { switch (notification) { diff --git a/Source/WebKit2/WebProcess/Plugins/PluginView.h b/Source/WebKit2/WebProcess/Plugins/PluginView.h index 0d0dfa344..59f0f8403 100644 --- a/Source/WebKit2/WebProcess/Plugins/PluginView.h +++ b/Source/WebKit2/WebProcess/Plugins/PluginView.h @@ -90,6 +90,8 @@ public: virtual bool handleEditingCommand(const String& commandName, const String& argument); virtual bool isEditingCommandEnabled(const String& commandName); + bool shouldAllowScripting(); + private: PluginView(PassRefPtr<WebCore::HTMLPlugInElement>, PassRefPtr<Plugin>, const Plugin::Parameters& parameters); virtual ~PluginView(); diff --git a/Source/WebKit2/WebProcess/WebConnectionToUIProcess.cpp b/Source/WebKit2/WebProcess/WebConnectionToUIProcess.cpp index 9c142d8a8..61237be7a 100644 --- a/Source/WebKit2/WebProcess/WebConnectionToUIProcess.cpp +++ b/Source/WebKit2/WebProcess/WebConnectionToUIProcess.cpp @@ -27,24 +27,27 @@ #include "WebConnectionToUIProcess.h" #include "InjectedBundleUserMessageCoders.h" -#include "WebConnectionMessageKinds.h" +#include "WebConnectionMessages.h" #include "WebProcess.h" using namespace WebCore; namespace WebKit { -PassRefPtr<WebConnectionToUIProcess> WebConnectionToUIProcess::create(WebProcess* process, CoreIPC::Connection::Identifier connectionIdentifier, RunLoop* runLoop) +PassRefPtr<WebConnectionToUIProcess> WebConnectionToUIProcess::create(WebProcess* process) { - return adoptRef(new WebConnectionToUIProcess(process, connectionIdentifier, runLoop)); + return adoptRef(new WebConnectionToUIProcess(process)); } -WebConnectionToUIProcess::WebConnectionToUIProcess(WebProcess* process, CoreIPC::Connection::Identifier connectionIdentifier, RunLoop* runLoop) - : WebConnection(CoreIPC::Connection::createClientConnection(connectionIdentifier, this, runLoop)) - , m_process(process) +WebConnectionToUIProcess::WebConnectionToUIProcess(WebProcess* process) + : m_process(process) { - m_connection->setDidCloseOnConnectionWorkQueueCallback(ChildProcess::didCloseOnConnectionWorkQueue); - m_connection->setShouldExitOnSyncMessageSendFailure(true); + m_process->addMessageReceiver(Messages::WebConnection::messageReceiverName(), this); +} + +void WebConnectionToUIProcess::invalidate() +{ + m_process = 0; } // WebConnection @@ -60,37 +63,19 @@ bool WebConnectionToUIProcess::decodeMessageBody(CoreIPC::ArgumentDecoder& decod return decoder.decode(messageBodyDecoder); } -// CoreIPC::Connection::Client -void WebConnectionToUIProcess::didReceiveMessage(CoreIPC::Connection* connection, CoreIPC::MessageID messageID, CoreIPC::MessageDecoder& decoder) -{ - if (messageID.is<CoreIPC::MessageClassWebConnection>()) { - didReceiveWebConnectionMessage(connection, messageID, decoder); - return; - } - - m_process->didReceiveMessage(connection, messageID, decoder); -} - -void WebConnectionToUIProcess::didReceiveSyncMessage(CoreIPC::Connection* connection, CoreIPC::MessageID messageID, CoreIPC::MessageDecoder& decoder, OwnPtr<CoreIPC::MessageEncoder>& replyEncoder) -{ - m_process->didReceiveSyncMessage(connection, messageID, decoder, replyEncoder); -} - -void WebConnectionToUIProcess::didClose(CoreIPC::Connection* connection) +CoreIPC::Connection* WebConnectionToUIProcess::connection() const { - m_process->didClose(connection); + return m_process->connection(); } -void WebConnectionToUIProcess::didReceiveInvalidMessage(CoreIPC::Connection* connection, CoreIPC::StringReference messageReceiverName, CoreIPC::StringReference messageName) +uint64_t WebConnectionToUIProcess::destinationID() const { - m_process->didReceiveInvalidMessage(connection, messageReceiverName, messageName); + return 0; } -#if PLATFORM(WIN) -Vector<HWND> WebConnectionToUIProcess::windowsToReceiveSentMessagesWhileWaitingForSyncReply() +bool WebConnectionToUIProcess::hasValidConnection() const { - return m_process->windowsToReceiveSentMessagesWhileWaitingForSyncReply(); + return m_process; } -#endif } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebConnectionToUIProcess.h b/Source/WebKit2/WebProcess/WebConnectionToUIProcess.h index 7f3f1fdb1..a78d82c98 100644 --- a/Source/WebKit2/WebProcess/WebConnectionToUIProcess.h +++ b/Source/WebKit2/WebProcess/WebConnectionToUIProcess.h @@ -26,32 +26,27 @@ #ifndef WebConnectionToUIProcess_h #define WebConnectionToUIProcess_h -#include "Connection.h" #include "WebConnection.h" namespace WebKit { class WebProcess; -class WebConnectionToUIProcess : public WebConnection, CoreIPC::Connection::Client { +class WebConnectionToUIProcess : public WebConnection { public: - static PassRefPtr<WebConnectionToUIProcess> create(WebProcess*, CoreIPC::Connection::Identifier, WebCore::RunLoop*); + static PassRefPtr<WebConnectionToUIProcess> create(WebProcess*); + + void invalidate(); private: - WebConnectionToUIProcess(WebProcess*, CoreIPC::Connection::Identifier, WebCore::RunLoop*); + WebConnectionToUIProcess(WebProcess*); // WebConnection virtual void encodeMessageBody(CoreIPC::ArgumentEncoder&, APIObject*) OVERRIDE; virtual bool decodeMessageBody(CoreIPC::ArgumentDecoder&, RefPtr<APIObject>&) OVERRIDE; - - // CoreIPC::Connection::Client - virtual void didReceiveMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&) OVERRIDE; - virtual void didReceiveSyncMessage(CoreIPC::Connection*, CoreIPC::MessageID, CoreIPC::MessageDecoder&, OwnPtr<CoreIPC::MessageEncoder>&) OVERRIDE; - virtual void didClose(CoreIPC::Connection*); - virtual void didReceiveInvalidMessage(CoreIPC::Connection*, CoreIPC::StringReference messageReceiverName, CoreIPC::StringReference messageName) OVERRIDE; -#if PLATFORM(WIN) - virtual Vector<HWND> windowsToReceiveSentMessagesWhileWaitingForSyncReply(); -#endif + virtual CoreIPC::Connection* connection() const OVERRIDE; + virtual uint64_t destinationID() const OVERRIDE; + virtual bool hasValidConnection() const OVERRIDE; WebProcess* m_process; }; diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp b/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp index 3e7fe3294..2a5da5c59 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp +++ b/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp @@ -118,7 +118,11 @@ FloatRect WebChromeClient::windowRect() FloatRect WebChromeClient::pageRect() { +#if USE(TILED_BACKING_STORE) + return FloatRect(FloatPoint(), m_page->viewportSize()); +#else return FloatRect(FloatPoint(), m_page->size()); +#endif } void WebChromeClient::focus() diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.cpp b/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.cpp index dd3e50926..b3df3b58f 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.cpp +++ b/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.cpp @@ -67,6 +67,7 @@ #include <WebCore/NotImplemented.h> #include <WebCore/Page.h> #include <WebCore/PluginData.h> +#include <WebCore/PluginDocument.h> #include <WebCore/ProgressTracker.h> #include <WebCore/ResourceBuffer.h> #include <WebCore/ResourceError.h> @@ -201,7 +202,6 @@ bool WebFrameLoaderClient::shouldUseCredentialStorage(DocumentLoader*, unsigned return webPage->injectedBundleResourceLoadClient().shouldUseCredentialStorage(webPage, m_frame, identifier); } -#if !PLATFORM(GTK) void WebFrameLoaderClient::dispatchDidReceiveAuthenticationChallenge(DocumentLoader*, unsigned long, const AuthenticationChallenge& challenge) { // FIXME: Authentication is a per-resource concept, but we don't do per-resource handling in the UIProcess at the API level quite yet. @@ -213,7 +213,6 @@ void WebFrameLoaderClient::dispatchDidReceiveAuthenticationChallenge(DocumentLoa AuthenticationManager::shared().didReceiveAuthenticationChallenge(m_frame, challenge); } -#endif void WebFrameLoaderClient::dispatchDidCancelAuthenticationChallenge(DocumentLoader*, unsigned long /*identifier*/, const AuthenticationChallenge&) { @@ -1630,6 +1629,27 @@ void WebFrameLoaderClient::didChangeScrollOffset() webPage->didChangeScrollOffsetForMainFrame(); } +bool WebFrameLoaderClient::allowScript(bool enabledPerSettings) +{ + if (!enabledPerSettings) + return false; + + Frame* coreFrame = m_frame->coreFrame(); + + if (coreFrame->document()->isPluginDocument()) { + PluginDocument* pluginDocument = static_cast<PluginDocument*>(coreFrame->document()); + + if (pluginDocument->pluginWidget() && pluginDocument->pluginWidget()->isPluginView()) { + PluginView* pluginView = static_cast<PluginView*>(pluginDocument->pluginWidget()); + + if (!pluginView->shouldAllowScripting()) + return false; + } + } + + return true; +} + bool WebFrameLoaderClient::shouldForceUniversalAccessFromLocalURL(const WebCore::KURL& url) { WebPage* webPage = m_frame->page(); diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.h b/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.h index 56e121f52..077b705bc 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.h +++ b/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.h @@ -235,6 +235,8 @@ private: virtual void didChangeScrollOffset() OVERRIDE; + virtual bool allowScript(bool enabledPerSettings) OVERRIDE; + virtual bool shouldForceUniversalAccessFromLocalURL(const WebCore::KURL&) OVERRIDE; virtual PassRefPtr<WebCore::FrameNetworkingContext> createNetworkingContext() OVERRIDE; diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.cpp b/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.cpp index f12b85196..c04664439 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.cpp +++ b/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.cpp @@ -42,6 +42,11 @@ #include <WebCore/PlatformPasteboard.h> #include <wtf/Atomics.h> +#if PLATFORM(WIN) && USE(CFNETWORK) +#include "WebFrameNetworkingContext.h" +#include <WebKitSystemInterface/WebKitSystemInterface.h> +#endif + #if USE(CF) #include <wtf/RetainPtr.h> #endif @@ -101,6 +106,13 @@ void WebPlatformStrategies::notifyCookiesChanged() WebCookieManager::shared().dispatchCookiesDidChange(); } +#if PLATFORM(WIN) && USE(CFNETWORK) +RetainPtr<CFHTTPCookieStorageRef> WebPlatformStrategies::defaultCookieStorage() +{ + return 0; +} +#endif + // LoaderStrategy #if ENABLE(NETWORK_PROCESS) diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.h b/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.h index bb644b1ab..040cfb1a9 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.h +++ b/Source/WebKit2/WebProcess/WebCoreSupport/WebPlatformStrategies.h @@ -55,6 +55,9 @@ private: // WebCore::CookiesStrategy virtual void notifyCookiesChanged() OVERRIDE; +#if PLATFORM(MAC) || USE(CFNETWORK) + virtual RetainPtr<CFHTTPCookieStorageRef> defaultCookieStorage() OVERRIDE; +#endif // WebCore::LoaderStrategy #if ENABLE(NETWORK_PROCESS) diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/gtk/WebFrameLoaderClientGtk.cpp b/Source/WebKit2/WebProcess/WebCoreSupport/gtk/WebFrameLoaderClientGtk.cpp deleted file mode 100644 index a6ff36e5f..000000000 --- a/Source/WebKit2/WebProcess/WebCoreSupport/gtk/WebFrameLoaderClientGtk.cpp +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Copyright (C) 2012, Igalia S.L. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY IGALIA S.L. AND ITS CONTRIBUTORS ``AS IS'' - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, - * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS - * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF - * THE POSSIBILITY OF SUCH DAMAGE. - */ -#include "config.h" -#include "WebFrameLoaderClient.h" - -#include <WebCore/AuthenticationChallenge.h> -#include <WebCore/GtkAuthenticationDialog.h> -#include <WebCore/ResourceHandle.h> - -namespace WebKit { - -using WebCore::GtkAuthenticationDialog; -using WebCore::AuthenticationChallenge; - -void WebFrameLoaderClient::dispatchDidReceiveAuthenticationChallenge(WebCore::DocumentLoader*, unsigned long, const AuthenticationChallenge& challenge) -{ - GtkAuthenticationDialog* dialog = new GtkAuthenticationDialog(0, challenge); - dialog->show(); -} - -} // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.h b/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.h index 32a0591ef..7124da825 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.h +++ b/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.h @@ -20,9 +20,9 @@ #ifndef WebFrameNetworkingContext_h #define WebFrameNetworkingContext_h +#include "HTTPCookieAcceptPolicy.h" #include "WebFrame.h" - -#import <WebCore/FrameNetworkingContext.h> +#include <WebCore/FrameNetworkingContext.h> namespace WebKit { @@ -33,16 +33,24 @@ public: return adoptRef(new WebFrameNetworkingContext(frame)); } + static void setPrivateBrowsingStorageSessionIdentifierBase(const String&); + static void switchToNewTestingSession(); + static void ensurePrivateBrowsingSession(); + static void destroyPrivateBrowsingSession(); + static CFURLStorageSessionRef defaultStorageSession(); + static void setCookieAcceptPolicyForAllContexts(HTTPCookieAcceptPolicy); + private: WebFrameNetworkingContext(WebFrame* frame) : WebCore::FrameNetworkingContext(frame->coreFrame()) { } - virtual bool needsSiteSpecificQuirks() const; - virtual bool localFileContentSniffingEnabled() const; - virtual WebCore::SchedulePairHashSet* scheduledRunLoopPairs() const; - virtual WebCore::ResourceError blockedError(const WebCore::ResourceRequest&) const; + virtual bool needsSiteSpecificQuirks() const OVERRIDE; + virtual bool localFileContentSniffingEnabled() const OVERRIDE; + virtual CFURLStorageSessionRef storageSession() const OVERRIDE; + virtual WebCore::SchedulePairHashSet* scheduledRunLoopPairs() const OVERRIDE; + virtual WebCore::ResourceError blockedError(const WebCore::ResourceRequest&) const OVERRIDE; }; } diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.mm b/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.mm index a95447174..b9c98d9c9 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.mm +++ b/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebFrameNetworkingContext.mm @@ -1,5 +1,6 @@ /* Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies) + Copyright (C) 2012 Apple Inc. All rights reserved. This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public @@ -20,15 +21,20 @@ #import "config.h" #import "WebFrameNetworkingContext.h" +#import <WebCore/CookieStorageCFNet.h> #import <WebCore/FrameLoaderClient.h> #import <WebCore/Page.h> #import <WebCore/ResourceError.h> #import <WebCore/Settings.h> +#import <WebKitSystemInterface.h> using namespace WebCore; namespace WebKit { +static CFURLStorageSessionRef defaultCFStorageSession; +static CFURLStorageSessionRef privateBrowsingStorageSession; + bool WebFrameNetworkingContext::needsSiteSpecificQuirks() const { return frame() && frame()->settings() && frame()->settings()->needsSiteSpecificQuirks(); @@ -49,4 +55,73 @@ ResourceError WebFrameNetworkingContext::blockedError(const ResourceRequest& req return frame()->loader()->client()->blockedError(request); } +static String& privateBrowsingStorageSessionIdentifierBase() +{ + ASSERT(isMainThread()); + DEFINE_STATIC_LOCAL(String, base, ()); + return base; +} + +void WebFrameNetworkingContext::setPrivateBrowsingStorageSessionIdentifierBase(const String& identifier) +{ + privateBrowsingStorageSessionIdentifierBase() = identifier; +} + +void WebFrameNetworkingContext::switchToNewTestingSession() +{ + // Set a private session for testing to avoid interfering with global cookies. This should be different from private browsing session. + if (defaultCFStorageSession) + CFRelease(defaultCFStorageSession); + defaultCFStorageSession = WKCreatePrivateStorageSession(CFSTR("Private WebKit Session")); +} + +void WebFrameNetworkingContext::ensurePrivateBrowsingSession() +{ + ASSERT(isMainThread()); + if (privateBrowsingStorageSession) + return; + + String base = privateBrowsingStorageSessionIdentifierBase().isNull() ? String([[NSBundle mainBundle] bundleIdentifier]) : privateBrowsingStorageSessionIdentifierBase(); + RetainPtr<CFStringRef> cfIdentifier = String(base + ".PrivateBrowsing").createCFString(); + + privateBrowsingStorageSession = WKCreatePrivateStorageSession(cfIdentifier.get()); +} + +void WebFrameNetworkingContext::destroyPrivateBrowsingSession() +{ + if (!privateBrowsingStorageSession) + return; + + CFRelease(privateBrowsingStorageSession); + privateBrowsingStorageSession = 0; +} + +CFURLStorageSessionRef WebFrameNetworkingContext::defaultStorageSession() +{ + return defaultCFStorageSession; +} + +CFURLStorageSessionRef WebFrameNetworkingContext::storageSession() const +{ + bool privateBrowsingEnabled = frame() && frame()->settings() && frame()->settings()->privateBrowsingEnabled(); + if (privateBrowsingEnabled) { + ASSERT(privateBrowsingStorageSession); + return privateBrowsingStorageSession; + } + return defaultCFStorageSession; +} + +void WebFrameNetworkingContext::setCookieAcceptPolicyForAllContexts(HTTPCookieAcceptPolicy policy) +{ + [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookieAcceptPolicy:static_cast<NSHTTPCookieAcceptPolicy>(policy)]; + + if (RetainPtr<CFHTTPCookieStorageRef> cookieStorage = defaultCFHTTPCookieStorage()) + WKSetHTTPCookieAcceptPolicy(cookieStorage.get(), policy); + + if (privateBrowsingStorageSession) { + RetainPtr<CFHTTPCookieStorageRef> privateBrowsingCookieStorage = adoptCF(WKCopyHTTPCookieStorage(privateBrowsingStorageSession)); + WKSetHTTPCookieAcceptPolicy(privateBrowsingCookieStorage.get(), policy); + } +} + } diff --git a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeController.mm b/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebPlatformStrategiesMac.mm index 43b895d28..c3341b7c4 100644 --- a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeController.mm +++ b/Source/WebKit2/WebProcess/WebCoreSupport/mac/WebPlatformStrategiesMac.mm @@ -23,32 +23,27 @@ * THE POSSIBILITY OF SUCH DAMAGE. */ -#import "config.h" -#import "RemoteLayerTreeController.h" +#include "config.h" +#include "WebPlatformStrategies.h" -#import "RemoteGraphicsLayer.h" -#import <wtf/PassOwnPtr.h> +#include "WebFrameNetworkingContext.h" +#include <WebKitSystemInterface.h> using namespace WebCore; namespace WebKit { -PassOwnPtr<RemoteLayerTreeController> RemoteLayerTreeController::create() +RetainPtr<CFHTTPCookieStorageRef> WebPlatformStrategies::defaultCookieStorage() { - return adoptPtr(new RemoteLayerTreeController); -} - -RemoteLayerTreeController::RemoteLayerTreeController() -{ -} - -RemoteLayerTreeController::~RemoteLayerTreeController() -{ -} - -PassOwnPtr<GraphicsLayer> RemoteLayerTreeController::createGraphicsLayer(GraphicsLayerClient* client) -{ - return RemoteGraphicsLayer::create(client, this); + if (CFURLStorageSessionRef session = WebFrameNetworkingContext::defaultStorageSession()) + return adoptCF(WKCopyHTTPCookieStorage(session)); + +#if USE(CFNETWORK) + return WKGetDefaultHTTPCookieStorage(); +#else + // When using NSURLConnection, we also use its shared cookie storage. + return 0; +#endif } } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/win/WebFrameNetworkingContext.h b/Source/WebKit2/WebProcess/WebCoreSupport/win/WebFrameNetworkingContext.h index 5f3f55765..252b703b7 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/win/WebFrameNetworkingContext.h +++ b/Source/WebKit2/WebProcess/WebCoreSupport/win/WebFrameNetworkingContext.h @@ -39,11 +39,15 @@ private: { } - virtual WTF::String userAgent() const; - virtual WTF::String referrer() const; + virtual String userAgent() const; + virtual String referrer() const; virtual WebCore::ResourceError blockedError(const WebCore::ResourceRequest&) const; - WTF::String m_userAgent; +#if USE(CFNETWORK) + virtual CFURLStorageSessionRef storageSession() const; +#endif + + String m_userAgent; }; #endif // WebFrameNetworkingContext_h diff --git a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.cpp b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.cpp index 26e48d61c..c167d3abb 100644 --- a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.cpp +++ b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.cpp @@ -1,5 +1,6 @@ /* Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies) + Copyright (C) 2012 Company 100, Inc. This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public @@ -82,6 +83,13 @@ void CoordinatedGraphicsLayer::didChangeFilters() } #endif +void CoordinatedGraphicsLayer::didChangeImageBacking() +{ + m_shouldSyncImageBacking = true; + if (client()) + client()->notifyFlushRequired(this); +} + void CoordinatedGraphicsLayer::setShouldUpdateVisibleRect() { m_shouldUpdateVisibleRect = true; @@ -105,11 +113,15 @@ CoordinatedGraphicsLayer::CoordinatedGraphicsLayer(GraphicsLayerClient* client) , m_shouldSyncLayerState(true) , m_shouldSyncChildren(true) , m_shouldSyncFilters(true) + , m_shouldSyncImageBacking(true) , m_shouldSyncAnimations(true) , m_fixedToViewport(false) , m_canvasNeedsDisplay(false) - , m_CoordinatedGraphicsLayerClient(0) + , m_canvasNeedsCreate(false) + , m_canvasNeedsDestroy(false) + , m_coordinator(0) , m_contentsScale(1) + , m_compositedNativeImagePtr(0) , m_canvasPlatformLayer(0) , m_animationStartedTimer(this, &CoordinatedGraphicsLayer::animationStartedTimerFired) { @@ -122,9 +134,9 @@ CoordinatedGraphicsLayer::~CoordinatedGraphicsLayer() { layerByIDMap().remove(id()); - if (m_CoordinatedGraphicsLayerClient) { + if (m_coordinator) { purgeBackingStores(); - m_CoordinatedGraphicsLayerClient->detachLayer(this); + m_coordinator->detachLayer(this); } willBeDestroyed(); } @@ -134,11 +146,6 @@ bool CoordinatedGraphicsLayer::setChildren(const Vector<GraphicsLayer*>& childre bool ok = GraphicsLayer::setChildren(children); if (!ok) return false; - for (unsigned i = 0; i < children.size(); ++i) { - CoordinatedGraphicsLayer* child = toCoordinatedGraphicsLayer(children[i]); - child->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); - child->didChangeLayerState(); - } didChangeChildren(); return true; } @@ -146,32 +153,24 @@ bool CoordinatedGraphicsLayer::setChildren(const Vector<GraphicsLayer*>& childre void CoordinatedGraphicsLayer::addChild(GraphicsLayer* layer) { GraphicsLayer::addChild(layer); - toCoordinatedGraphicsLayer(layer)->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); - toCoordinatedGraphicsLayer(layer)->didChangeLayerState(); didChangeChildren(); } void CoordinatedGraphicsLayer::addChildAtIndex(GraphicsLayer* layer, int index) { GraphicsLayer::addChildAtIndex(layer, index); - toCoordinatedGraphicsLayer(layer)->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); - toCoordinatedGraphicsLayer(layer)->didChangeLayerState(); didChangeChildren(); } void CoordinatedGraphicsLayer::addChildAbove(GraphicsLayer* layer, GraphicsLayer* sibling) { GraphicsLayer::addChildAbove(layer, sibling); - toCoordinatedGraphicsLayer(layer)->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); - toCoordinatedGraphicsLayer(layer)->didChangeLayerState(); didChangeChildren(); } void CoordinatedGraphicsLayer::addChildBelow(GraphicsLayer* layer, GraphicsLayer* sibling) { GraphicsLayer::addChildBelow(layer, sibling); - toCoordinatedGraphicsLayer(layer)->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); - toCoordinatedGraphicsLayer(layer)->didChangeLayerState(); didChangeChildren(); } @@ -181,9 +180,6 @@ bool CoordinatedGraphicsLayer::replaceChild(GraphicsLayer* oldChild, GraphicsLay if (!ok) return false; didChangeChildren(); - toCoordinatedGraphicsLayer(oldChild)->didChangeLayerState(); - toCoordinatedGraphicsLayer(newChild)->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); - toCoordinatedGraphicsLayer(newChild)->didChangeLayerState(); return true; } @@ -192,8 +188,6 @@ void CoordinatedGraphicsLayer::removeFromParent() if (CoordinatedGraphicsLayer* parentLayer = toCoordinatedGraphicsLayer(parent())) parentLayer->didChangeChildren(); GraphicsLayer::removeFromParent(); - - didChangeLayerState(); } void CoordinatedGraphicsLayer::setPosition(const FloatPoint& p) @@ -318,20 +312,40 @@ void CoordinatedGraphicsLayer::setContentsRect(const IntRect& r) void CoordinatedGraphicsLayer::setContentsNeedsDisplay() { - RefPtr<Image> image = m_image; - setContentsToImage(0); - setContentsToImage(image.get()); - m_canvasNeedsDisplay = true; + if (m_canvasPlatformLayer) + m_canvasNeedsDisplay = true; if (client()) client()->notifyFlushRequired(this); } void CoordinatedGraphicsLayer::setContentsToCanvas(PlatformLayer* platformLayer) { +#if USE(GRAPHICS_SURFACE) + if (m_canvasPlatformLayer) { + ASSERT(m_canvasToken.isValid()); + if (!platformLayer) + m_canvasNeedsDestroy = true; + else if (m_canvasToken != platformLayer->graphicsSurfaceToken()) { + // m_canvasToken can be different to platformLayer->graphicsSurfaceToken(), even if m_canvasPlatformLayer equals platformLayer. + m_canvasNeedsDestroy = true; + m_canvasNeedsCreate = true; + } + } else { + if (platformLayer) + m_canvasNeedsCreate = true; + } + m_canvasPlatformLayer = platformLayer; - m_canvasNeedsDisplay = true; + // m_canvasToken is updated only here. In detail, when GraphicsContext3D is changed or reshaped, m_canvasToken is changed and setContentsToCanvas() is always called. + m_canvasToken = m_canvasPlatformLayer ? m_canvasPlatformLayer->graphicsSurfaceToken() : GraphicsSurfaceToken(); + ASSERT(!(!m_canvasToken.isValid() && m_canvasPlatformLayer)); + if (m_canvasPlatformLayer) + m_canvasNeedsDisplay = true; if (client()) client()->notifyFlushRequired(this); +#else + UNUSED_PARAM(platformLayer); +#endif } #if ENABLE(CSS_FILTERS) @@ -347,25 +361,22 @@ bool CoordinatedGraphicsLayer::setFilters(const FilterOperations& newFilters) void CoordinatedGraphicsLayer::setContentsToImage(Image* image) { - if (image == m_image) - return; - int64_t newID = 0; - if (m_CoordinatedGraphicsLayerClient) { - // We adopt first, in case this is the same frame - that way we avoid destroying and recreating the image. - newID = m_CoordinatedGraphicsLayerClient->adoptImageBackingStore(image); - m_CoordinatedGraphicsLayerClient->releaseImageBackingStore(m_layerInfo.imageBackingStoreID); - didChangeLayerState(); - if (m_layerInfo.imageBackingStoreID && newID == m_layerInfo.imageBackingStoreID) + NativeImagePtr newNativeImagePtr = image ? image->nativeImageForCurrentFrame() : 0; + if (newNativeImagePtr) { + // This code makes the assumption that pointer equality on a NativeImagePtr is a valid way to tell if the image is changed. + // This assumption is true in Qt, GTK and EFL. + if (newNativeImagePtr == m_compositedNativeImagePtr) return; + + m_compositedImage = image; + m_compositedNativeImagePtr = newNativeImagePtr; } else { - // If m_CoordinatedGraphicsLayerClient is not set yet there should be no backing store ID. - ASSERT(!m_layerInfo.imageBackingStoreID); - didChangeLayerState(); + m_compositedImage = 0; + m_compositedNativeImagePtr = 0; } - m_layerInfo.imageBackingStoreID = newID; - m_image = image; GraphicsLayer::setContentsToImage(image); + didChangeImageBacking(); } void CoordinatedGraphicsLayer::setMaskLayer(GraphicsLayer* layer) @@ -380,21 +391,29 @@ void CoordinatedGraphicsLayer::setMaskLayer(GraphicsLayer* layer) layer->setSize(size()); CoordinatedGraphicsLayer* CoordinatedGraphicsLayer = toCoordinatedGraphicsLayer(layer); - CoordinatedGraphicsLayer->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); CoordinatedGraphicsLayer->setMaskTarget(this); CoordinatedGraphicsLayer->didChangeLayerState(); didChangeLayerState(); } +bool CoordinatedGraphicsLayer::shouldDirectlyCompositeImage(Image* image) const +{ + if (!image || !image->isBitmapImage()) + return false; + + enum { kMaxDimenstionForDirectCompositing = 2000 }; + if (image->width() > kMaxDimenstionForDirectCompositing || image->height() > kMaxDimenstionForDirectCompositing) + return false; + + return true; +} + void CoordinatedGraphicsLayer::setReplicatedByLayer(GraphicsLayer* layer) { if (layer == replicaLayer()) return; - if (layer) - toCoordinatedGraphicsLayer(layer)->setCoordinatedGraphicsLayerClient(m_CoordinatedGraphicsLayerClient); - GraphicsLayer::setReplicatedByLayer(layer); didChangeLayerState(); } @@ -424,7 +443,7 @@ void CoordinatedGraphicsLayer::flushCompositingState(const FloatRect& rect) if (CoordinatedGraphicsLayer* replica = toCoordinatedGraphicsLayer(replicaLayer())) replica->flushCompositingStateForThisLayerOnly(); - m_CoordinatedGraphicsLayerClient->syncFixedLayers(); + m_coordinator->syncFixedLayers(); flushCompositingStateForThisLayerOnly(); @@ -446,7 +465,7 @@ void CoordinatedGraphicsLayer::syncChildren() for (size_t i = 0; i < children().size(); ++i) childIDs.append(toWebLayerID(children()[i])); - m_CoordinatedGraphicsLayerClient->syncLayerChildren(m_id, childIDs); + m_coordinator->syncLayerChildren(m_id, childIDs); } #if ENABLE(CSS_FILTERS) @@ -455,10 +474,38 @@ void CoordinatedGraphicsLayer::syncFilters() if (!m_shouldSyncFilters) return; m_shouldSyncFilters = false; - m_CoordinatedGraphicsLayerClient->syncLayerFilters(m_id, filters()); + m_coordinator->syncLayerFilters(m_id, filters()); } #endif +void CoordinatedGraphicsLayer::syncImageBacking() +{ + if (!m_shouldSyncImageBacking) + return; + m_shouldSyncImageBacking = false; + + if (m_compositedNativeImagePtr) { + ASSERT(!m_mainBackingStore); + ASSERT(m_compositedImage); + + bool imageInstanceReplaced = m_coordinatedImageBacking && (m_coordinatedImageBacking->id() != CoordinatedImageBacking::getCoordinatedImageBackingID(m_compositedImage.get())); + if (imageInstanceReplaced) + releaseImageBackingIfNeeded(); + + if (!m_coordinatedImageBacking) { + m_coordinatedImageBacking = m_coordinator->createImageBackingIfNeeded(m_compositedImage.get()); + m_coordinatedImageBacking->addHost(this); + m_layerInfo.imageID = m_coordinatedImageBacking->id(); + } + + m_coordinatedImageBacking->markDirty(); + } else + releaseImageBackingIfNeeded(); + + // syncImageBacking() changed m_layerInfo.imageID. + didChangeLayerState(); +} + void CoordinatedGraphicsLayer::syncLayerState() { if (!m_shouldSyncLayerState) @@ -481,7 +528,7 @@ void CoordinatedGraphicsLayer::syncLayerState() m_layerInfo.replica = toWebLayerID(replicaLayer()); m_layerInfo.size = size(); m_layerInfo.transform = transform(); - m_CoordinatedGraphicsLayerClient->syncLayerState(m_id, m_layerInfo); + m_coordinator->syncLayerState(m_id, m_layerInfo); } void CoordinatedGraphicsLayer::syncAnimations() @@ -491,38 +538,50 @@ void CoordinatedGraphicsLayer::syncAnimations() m_shouldSyncAnimations = false; - m_CoordinatedGraphicsLayerClient->setLayerAnimations(m_id, m_animations); + m_coordinator->setLayerAnimations(m_id, m_animations); } void CoordinatedGraphicsLayer::syncCanvas() { + destroyCanvasIfNeeded(); + createCanvasIfNeeded(); + if (!m_canvasNeedsDisplay) return; - if (!m_canvasPlatformLayer) + ASSERT(m_canvasPlatformLayer); +#if USE(GRAPHICS_SURFACE) + m_coordinator->syncCanvas(m_id, m_canvasPlatformLayer); +#endif + m_canvasNeedsDisplay = false; +} + +void CoordinatedGraphicsLayer::destroyCanvasIfNeeded() +{ + if (!m_canvasNeedsDestroy) return; #if USE(GRAPHICS_SURFACE) - uint32_t frontBuffer = m_canvasPlatformLayer->copyToGraphicsSurface(); - GraphicsSurfaceToken token = m_canvasPlatformLayer->graphicsSurfaceToken(); - - m_CoordinatedGraphicsLayerClient->syncCanvas(m_id, IntSize(size().width(), size().height()), token, frontBuffer); + m_coordinator->destroyCanvas(m_id); #endif - m_canvasNeedsDisplay = false; + m_canvasNeedsDestroy = false; } -void CoordinatedGraphicsLayer::ensureImageBackingStore() +void CoordinatedGraphicsLayer::createCanvasIfNeeded() { - if (!m_image) + if (!m_canvasNeedsCreate) return; - if (!m_layerInfo.imageBackingStoreID) - m_layerInfo.imageBackingStoreID = m_CoordinatedGraphicsLayerClient->adoptImageBackingStore(m_image.get()); + + ASSERT(m_canvasPlatformLayer); +#if USE(GRAPHICS_SURFACE) + m_coordinator->createCanvas(m_id, m_canvasPlatformLayer); +#endif + m_canvasNeedsCreate = false; } void CoordinatedGraphicsLayer::flushCompositingStateForThisLayerOnly() { - // The remote image might have been released by purgeBackingStores. - ensureImageBackingStore(); + syncImageBacking(); syncLayerState(); syncAnimations(); computeTransformedVisibleRect(); @@ -534,6 +593,23 @@ void CoordinatedGraphicsLayer::flushCompositingStateForThisLayerOnly() syncCanvas(); } +bool CoordinatedGraphicsLayer::imageBackingVisible() +{ + ASSERT(m_coordinatedImageBacking); + return tiledBackingStoreVisibleRect().intersects(contentsRect()); +} + +void CoordinatedGraphicsLayer::releaseImageBackingIfNeeded() +{ + if (!m_coordinatedImageBacking) + return; + + ASSERT(m_coordinator); + m_coordinatedImageBacking->removeHost(this); + m_coordinatedImageBacking.clear(); + m_layerInfo.imageID = InvalidCoordinatedImageBackingID; +} + void CoordinatedGraphicsLayer::tiledBackingStorePaintBegin() { } @@ -558,12 +634,12 @@ void CoordinatedGraphicsLayer::setContentsScale(float scale) float CoordinatedGraphicsLayer::effectiveContentsScale() { - return shouldUseTiledBackingStore() ? m_contentsScale : 1; + return selfOrAncestorHaveNonAffineTransforms() ? 1 : m_contentsScale; } void CoordinatedGraphicsLayer::adjustContentsScale() { - if (!drawsContent()) + if (!drawsContent() || !contentsAreVisible() || m_size.isEmpty()) return; if (!m_mainBackingStore || m_mainBackingStore->contentsScale() == effectiveContentsScale()) @@ -603,7 +679,7 @@ bool CoordinatedGraphicsLayer::tiledBackingStoreUpdatesAllowed() const { if (!m_inUpdateMode) return false; - return m_CoordinatedGraphicsLayerClient->layerTreeTileUpdatesAllowed(); + return m_coordinator->layerTreeTileUpdatesAllowed(); } IntRect CoordinatedGraphicsLayer::tiledBackingStoreContentsRect() @@ -611,16 +687,21 @@ IntRect CoordinatedGraphicsLayer::tiledBackingStoreContentsRect() return IntRect(0, 0, size().width(), size().height()); } -bool CoordinatedGraphicsLayer::shouldUseTiledBackingStore() +static void clampToContentsRectIfRectIsInfinite(FloatRect& rect, const IntRect& contentsRect) { - return !selfOrAncestorHaveNonAffineTransforms(); + if (rect.width() >= LayoutUnit::nearlyMax() || rect.width() <= LayoutUnit::nearlyMin()) { + rect.setX(contentsRect.x()); + rect.setWidth(contentsRect.width()); + } + + if (rect.height() >= LayoutUnit::nearlyMax() || rect.height() <= LayoutUnit::nearlyMin()) { + rect.setY(contentsRect.y()); + rect.setHeight(contentsRect.height()); + } } IntRect CoordinatedGraphicsLayer::tiledBackingStoreVisibleRect() { - if (!shouldUseTiledBackingStore()) - return tiledBackingStoreContentsRect(); - // Non-invertible layers are not visible. if (!m_layerTransform.combined().isInvertible()) return IntRect(); @@ -628,7 +709,10 @@ IntRect CoordinatedGraphicsLayer::tiledBackingStoreVisibleRect() // Return a projection of the visible rect (surface coordinates) onto the layer's plane (layer coordinates). // The resulting quad might be squewed and the visible rect is the bounding box of this quad, // so it might spread further than the real visible area (and then even more amplified by the cover rect multiplier). - return enclosingIntRect(m_layerTransform.combined().inverse().clampedBoundsOfProjectedQuad(FloatQuad(FloatRect(m_CoordinatedGraphicsLayerClient->visibleContentsRect())))); + ASSERT(m_cachedInverseTransform == m_layerTransform.combined().inverse()); + FloatRect rect = m_cachedInverseTransform.clampedBoundsOfProjectedQuad(FloatQuad(FloatRect(m_coordinator->visibleContentsRect()))); + clampToContentsRectIfRectIsInfinite(rect, tiledBackingStoreContentsRect()); + return enclosingIntRect(rect); } Color CoordinatedGraphicsLayer::tiledBackingStoreBackgroundColor() const @@ -636,24 +720,30 @@ Color CoordinatedGraphicsLayer::tiledBackingStoreBackgroundColor() const return contentsOpaque() ? Color::white : Color::transparent; } -PassOwnPtr<WebCore::GraphicsContext> CoordinatedGraphicsLayer::beginContentUpdate(const WebCore::IntSize& size, int& atlas, WebCore::IntPoint& offset) +PassOwnPtr<GraphicsContext> CoordinatedGraphicsLayer::beginContentUpdate(const IntSize& size, int& atlas, IntPoint& offset) { - return m_CoordinatedGraphicsLayerClient->beginContentUpdate(size, contentsOpaque() ? 0 : ShareableBitmap::SupportsAlpha, atlas, offset); + if (!m_coordinator) + return PassOwnPtr<WebCore::GraphicsContext>(); + + return m_coordinator->beginContentUpdate(size, contentsOpaque() ? 0 : ShareableBitmap::SupportsAlpha, atlas, offset); } -void CoordinatedGraphicsLayer::createTile(int tileID, const SurfaceUpdateInfo& updateInfo, const IntRect& targetRect) +void CoordinatedGraphicsLayer::createTile(int tileID, const SurfaceUpdateInfo& updateInfo, const WebCore::IntRect& tileRect) { - m_CoordinatedGraphicsLayerClient->createTile(id(), tileID, updateInfo, targetRect); + if (m_coordinator) + m_coordinator->createTile(id(), tileID, updateInfo, tileRect); } -void CoordinatedGraphicsLayer::updateTile(int tileID, const SurfaceUpdateInfo& updateInfo, const IntRect& targetRect) +void CoordinatedGraphicsLayer::updateTile(int tileID, const SurfaceUpdateInfo& updateInfo, const IntRect& tileRect) { - m_CoordinatedGraphicsLayerClient->updateTile(id(), tileID, updateInfo, targetRect); + if (m_coordinator) + m_coordinator->updateTile(id(), tileID, updateInfo, tileRect); } void CoordinatedGraphicsLayer::removeTile(int tileID) { - m_CoordinatedGraphicsLayerClient->removeTile(id(), tileID); + if (m_coordinator) + m_coordinator->removeTile(id(), tileID); } void CoordinatedGraphicsLayer::updateContentBuffers() @@ -684,37 +774,14 @@ void CoordinatedGraphicsLayer::purgeBackingStores() m_mainBackingStore.clear(); m_previousBackingStore.clear(); - if (m_layerInfo.imageBackingStoreID) { - m_CoordinatedGraphicsLayerClient->releaseImageBackingStore(m_layerInfo.imageBackingStoreID); - m_layerInfo.imageBackingStoreID = 0; - } + releaseImageBackingIfNeeded(); didChangeLayerState(); - didChangeChildren(); } -void CoordinatedGraphicsLayer::setCoordinatedGraphicsLayerClient(WebKit::CoordinatedGraphicsLayerClient* client) +void CoordinatedGraphicsLayer::setCoordinator(WebKit::CoordinatedGraphicsLayerClient* coordinator) { - if (m_CoordinatedGraphicsLayerClient == client) - return; - - if (CoordinatedGraphicsLayer* replica = toCoordinatedGraphicsLayer(replicaLayer())) - replica->setCoordinatedGraphicsLayerClient(client); - if (CoordinatedGraphicsLayer* mask = toCoordinatedGraphicsLayer(maskLayer())) - mask->setCoordinatedGraphicsLayerClient(client); - for (size_t i = 0; i < children().size(); ++i) { - CoordinatedGraphicsLayer* layer = toCoordinatedGraphicsLayer(this->children()[i]); - layer->setCoordinatedGraphicsLayerClient(client); - } - - // We have to release resources on the UI process here if the remote client has changed or is removed. - if (m_CoordinatedGraphicsLayerClient) { - purgeBackingStores(); - m_CoordinatedGraphicsLayerClient->detachLayer(this); - } - m_CoordinatedGraphicsLayerClient = client; - if (client) - client->attachLayer(this); + m_coordinator = coordinator; } void CoordinatedGraphicsLayer::adjustVisibleRect() @@ -733,26 +800,31 @@ bool CoordinatedGraphicsLayer::hasPendingVisibleChanges() return true; } - if (!m_shouldSyncLayerState && !m_shouldSyncChildren && !m_shouldSyncFilters && !m_shouldSyncAnimations && !m_canvasNeedsDisplay) + if (!m_shouldSyncLayerState && !m_shouldSyncChildren && !m_shouldSyncFilters && !m_shouldSyncImageBacking && !m_shouldSyncAnimations && !m_canvasNeedsDisplay) return false; - return selfOrAncestorHaveNonAffineTransforms() || !tiledBackingStoreVisibleRect().isEmpty(); - + return tiledBackingStoreVisibleRect().intersects(tiledBackingStoreContentsRect()); } void CoordinatedGraphicsLayer::computeTransformedVisibleRect() { - if (!m_shouldUpdateVisibleRect) + // When we have a transform animation, we need to update visible rect every frame to adjust the visible rect of a backing store. + bool hasActiveTransformAnimation = selfOrAncestorHasActiveTransformAnimation(); + if (!m_shouldUpdateVisibleRect && !hasActiveTransformAnimation) return; m_shouldUpdateVisibleRect = false; - m_layerTransform.setLocalTransform(transform()); + TransformationMatrix currentTransform = transform(); + if (hasActiveTransformAnimation) + client()->getCurrentTransform(this, currentTransform); + m_layerTransform.setLocalTransform(currentTransform); m_layerTransform.setPosition(position()); m_layerTransform.setAnchorPoint(anchorPoint()); m_layerTransform.setSize(size()); m_layerTransform.setFlattening(!preserves3D()); m_layerTransform.setChildrenTransform(childrenTransform()); m_layerTransform.combineTransforms(parent() ? toCoordinatedGraphicsLayer(parent())->m_layerTransform.combinedForChildren() : TransformationMatrix()); + m_cachedInverseTransform = m_layerTransform.combined().inverse(); // The combined transform will be used in tiledBackingStoreVisibleRect. adjustVisibleRect(); @@ -769,6 +841,17 @@ void CoordinatedGraphicsLayer::initFactory() GraphicsLayer::setGraphicsLayerFactory(createCoordinatedGraphicsLayer); } +bool CoordinatedGraphicsLayer::selfOrAncestorHasActiveTransformAnimation() const +{ + if (m_animations.hasActiveAnimationsOfType(AnimatedPropertyWebkitTransform)) + return true; + + if (!parent()) + return false; + + return toCoordinatedGraphicsLayer(parent())->selfOrAncestorHasActiveTransformAnimation(); +} + bool CoordinatedGraphicsLayer::selfOrAncestorHaveNonAffineTransforms() { if (m_animations.hasActiveAnimationsOfType(AnimatedPropertyWebkitTransform)) @@ -812,6 +895,18 @@ void CoordinatedGraphicsLayer::removeAnimation(const String& animationName) didChangeAnimations(); } +void CoordinatedGraphicsLayer::suspendAnimations(double time) +{ + m_animations.suspend(time); + didChangeAnimations(); +} + +void CoordinatedGraphicsLayer::resumeAnimations() +{ + m_animations.resume(); + didChangeAnimations(); +} + void CoordinatedGraphicsLayer::animationStartedTimerFired(Timer<CoordinatedGraphicsLayer>*) { client()->notifyAnimationStarted(this, m_lastAnimationStartTime); diff --git a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.h b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.h index 1188aa75f..a903e6519 100644 --- a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.h +++ b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedGraphicsLayer.h @@ -21,12 +21,12 @@ #ifndef CoordinatedGraphicsLayer_h #define CoordinatedGraphicsLayer_h +#include "CoordinatedImageBacking.h" #include "CoordinatedTile.h" #include "FloatPoint3D.h" #include "GraphicsLayer.h" #include "GraphicsLayerAnimation.h" #include "GraphicsLayerTransform.h" -#include "GraphicsSurface.h" #include "Image.h" #include "IntSize.h" #include "ShareableBitmap.h" @@ -36,6 +36,9 @@ #include "UpdateInfo.h" #include "WebLayerTreeInfo.h" #include "WebProcess.h" +#if USE(GRAPHICS_SURFACE) +#include <WebCore/GraphicsSurfaceToken.h> +#endif #include <WebCore/RunLoop.h> #include <wtf/text/StringHash.h> @@ -56,20 +59,20 @@ public: virtual WebCore::IntRect visibleContentsRect() const = 0; virtual bool layerTreeTileUpdatesAllowed() const = 0; - virtual int64_t adoptImageBackingStore(WebCore::Image*) = 0; - virtual void releaseImageBackingStore(int64_t) = 0; + virtual PassRefPtr<CoordinatedImageBacking> createImageBackingIfNeeded(WebCore::Image*) = 0; virtual void syncLayerState(WebLayerID, const WebLayerInfo&) = 0; virtual void syncLayerChildren(WebLayerID, const Vector<WebLayerID>&) = 0; #if ENABLE(CSS_FILTERS) virtual void syncLayerFilters(WebLayerID, const WebCore::FilterOperations&) = 0; #endif #if USE(GRAPHICS_SURFACE) - virtual void syncCanvas(WebLayerID, const WebCore::IntSize& canvasSize, const WebCore::GraphicsSurfaceToken&, uint32_t frontBuffer) = 0; + virtual void createCanvas(WebLayerID, WebCore::PlatformLayer*) = 0; + virtual void syncCanvas(WebLayerID, WebCore::PlatformLayer*) = 0; + virtual void destroyCanvas(WebLayerID) = 0; #endif virtual void setLayerAnimations(WebLayerID, const WebCore::GraphicsLayerAnimations&) = 0; - virtual void attachLayer(WebCore::CoordinatedGraphicsLayer*) = 0; virtual void detachLayer(WebCore::CoordinatedGraphicsLayer*) = 0; virtual void syncFixedLayers() = 0; virtual PassOwnPtr<WebCore::GraphicsContext> beginContentUpdate(const WebCore::IntSize&, ShareableBitmap::Flags, int& atlasID, WebCore::IntPoint&) = 0; @@ -80,9 +83,10 @@ namespace WebCore { class CoordinatedGraphicsLayer : public GraphicsLayer , public TiledBackingStoreClient + , public WebKit::CoordinatedImageBacking::Host , public WebKit::CoordinatedTileClient { public: - CoordinatedGraphicsLayer(GraphicsLayerClient*); + explicit CoordinatedGraphicsLayer(GraphicsLayerClient*); virtual ~CoordinatedGraphicsLayer(); // Reimplementations from GraphicsLayer.h. @@ -107,6 +111,7 @@ public: virtual void setOpacity(float) OVERRIDE; virtual void setContentsRect(const IntRect&) OVERRIDE; virtual void setContentsToImage(Image*) OVERRIDE; + virtual bool shouldDirectlyCompositeImage(Image*) const OVERRIDE; virtual void setContentsToCanvas(PlatformLayer*) OVERRIDE; virtual void setMaskLayer(GraphicsLayer*) OVERRIDE; virtual void setReplicatedByLayer(GraphicsLayer*) OVERRIDE; @@ -121,6 +126,8 @@ public: virtual bool addAnimation(const KeyframeValueList&, const IntSize&, const Animation*, const String&, double) OVERRIDE; virtual void pauseAnimation(const String&, double) OVERRIDE; virtual void removeAnimation(const String&) OVERRIDE; + virtual void suspendAnimations(double time) OVERRIDE; + virtual void resumeAnimations() OVERRIDE; void setContentsScale(float); void setVisibleContentRectTrajectoryVector(const FloatPoint&); @@ -150,7 +157,7 @@ public: virtual void removeTile(int tileID) OVERRIDE; virtual PassOwnPtr<GraphicsContext> beginContentUpdate(const IntSize&, int& atlasID, IntPoint&) OVERRIDE; - void setCoordinatedGraphicsLayerClient(WebKit::CoordinatedGraphicsLayerClient*); + void setCoordinator(WebKit::CoordinatedGraphicsLayerClient*); void adjustVisibleRect(); void purgeBackingStores(); @@ -160,7 +167,6 @@ private: bool fixedToViewport() const { return m_fixedToViewport; } void setMaskTarget(GraphicsLayer* layer) { m_maskTarget = layer; } - void notifyChange(); void didChangeLayerState(); void didChangeAnimations(); void didChangeGeometry(); @@ -168,6 +174,7 @@ private: #if ENABLE(CSS_FILTERS) void didChangeFilters(); #endif + void didChangeImageBacking(); void syncLayerState(); void syncAnimations(); @@ -175,15 +182,22 @@ private: #if ENABLE(CSS_FILTERS) void syncFilters(); #endif + void syncImageBacking(); void syncCanvas(); - void ensureImageBackingStore(); void computeTransformedVisibleRect(); void updateContentBuffers(); void createBackingStore(); + void releaseImageBackingIfNeeded(); + + // CoordinatedImageBacking::Host + virtual bool imageBackingVisible() OVERRIDE; + void destroyCanvasIfNeeded(); + void createCanvasIfNeeded(); + + bool selfOrAncestorHasActiveTransformAnimation() const; bool selfOrAncestorHaveNonAffineTransforms(); - bool shouldUseTiledBackingStore(); void adjustContentsScale(); void setShouldUpdateVisibleRect(); @@ -193,27 +207,34 @@ private: WebKit::WebLayerID m_id; WebKit::WebLayerInfo m_layerInfo; - RefPtr<Image> m_image; GraphicsLayer* m_maskTarget; - FloatRect m_needsDisplayRect; GraphicsLayerTransform m_layerTransform; + TransformationMatrix m_cachedInverseTransform; bool m_inUpdateMode : 1; bool m_shouldUpdateVisibleRect: 1; bool m_shouldSyncLayerState: 1; bool m_shouldSyncChildren: 1; bool m_shouldSyncFilters: 1; + bool m_shouldSyncImageBacking: 1; bool m_shouldSyncAnimations: 1; bool m_fixedToViewport : 1; bool m_canvasNeedsDisplay : 1; + bool m_canvasNeedsCreate : 1; + bool m_canvasNeedsDestroy : 1; - float m_effectiveOpacity; - TransformationMatrix m_effectiveTransform; - - WebKit::CoordinatedGraphicsLayerClient* m_CoordinatedGraphicsLayerClient; + WebKit::CoordinatedGraphicsLayerClient* m_coordinator; OwnPtr<TiledBackingStore> m_mainBackingStore; OwnPtr<TiledBackingStore> m_previousBackingStore; float m_contentsScale; + + RefPtr<Image> m_compositedImage; + NativeImagePtr m_compositedNativeImagePtr; + RefPtr<WebKit::CoordinatedImageBacking> m_coordinatedImageBacking; + PlatformLayer* m_canvasPlatformLayer; +#if USE(GRAPHICS_SURFACE) + GraphicsSurfaceToken m_canvasToken; +#endif Timer<CoordinatedGraphicsLayer> m_animationStartedTimer; GraphicsLayerAnimations m_animations; double m_lastAnimationStartTime; diff --git a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedImageBacking.cpp b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedImageBacking.cpp new file mode 100644 index 000000000..55ca9da7b --- /dev/null +++ b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedImageBacking.cpp @@ -0,0 +1,168 @@ +/* + * Copyright (C) 2012 Company 100, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include "config.h" + +#if USE(COORDINATED_GRAPHICS) +#include "CoordinatedImageBacking.h" + +#include "GraphicsContext.h" + +using namespace WebCore; + +namespace WebKit { + +CoordinatedImageBackingID CoordinatedImageBacking::getCoordinatedImageBackingID(Image* image) +{ + // CoordinatedImageBacking keeps a RefPtr<Image> member, so the same Image pointer can not refer two different instances until CoordinatedImageBacking releases the member. + return reinterpret_cast<CoordinatedImageBackingID>(image); +} + +PassRefPtr<CoordinatedImageBacking> CoordinatedImageBacking::create(Coordinator* client, PassRefPtr<Image> image) +{ + return adoptRef(new CoordinatedImageBacking(client, image)); +} + +CoordinatedImageBacking::CoordinatedImageBacking(Coordinator* client, PassRefPtr<Image> image) + : m_coordinator(client) + , m_image(image) + , m_id(getCoordinatedImageBackingID(m_image.get())) + , m_clearContentsTimer(this, &CoordinatedImageBacking::clearContentsTimerFired) + , m_isDirty(false) + , m_isVisible(false) +{ + // FIXME: We would need to decode a small image directly into a GraphicsSurface. + // http://webkit.org/b/101426 + + m_coordinator->createImageBacking(id()); +} + +CoordinatedImageBacking::~CoordinatedImageBacking() +{ +} + +void CoordinatedImageBacking::addHost(Host* host) +{ + ASSERT(!m_hosts.contains(host)); + m_hosts.append(host); +} + +void CoordinatedImageBacking::removeHost(Host* host) +{ + size_t position = m_hosts.find(host); + ASSERT(position != notFound); + m_hosts.remove(position); + + if (m_hosts.isEmpty()) + m_coordinator->removeImageBacking(id()); +} + +void CoordinatedImageBacking::markDirty() +{ + m_isDirty = true; +} + +void CoordinatedImageBacking::update() +{ + releaseSurfaceIfNeeded(); + + bool changedToVisible; + updateVisibilityIfNeeded(changedToVisible); + if (!m_isVisible) + return; + + if (!changedToVisible) { + if (!m_isDirty) + return; + + if (m_nativeImagePtr == m_image->nativeImageForCurrentFrame()) { + m_isDirty = false; + return; + } + } + + m_surface = ShareableSurface::create(m_image->size(), m_image->currentFrameHasAlpha() ? ShareableBitmap::SupportsAlpha : ShareableBitmap::NoFlags, ShareableSurface::SupportsGraphicsSurface); + m_handle = adoptPtr(new ShareableSurface::Handle()); + + if (!m_surface->createHandle(*m_handle)) { + releaseSurfaceIfNeeded(); + m_isDirty = false; + return; + } + + IntRect rect(IntPoint::zero(), m_image->size()); + OwnPtr<GraphicsContext> context = m_surface->createGraphicsContext(rect); + context->drawImage(m_image.get(), ColorSpaceDeviceRGB, rect, rect); + + m_nativeImagePtr = m_image->nativeImageForCurrentFrame(); + + m_coordinator->updateImageBacking(id(), *m_handle); + m_isDirty = false; +} + +void CoordinatedImageBacking::releaseSurfaceIfNeeded() +{ + // We must keep m_surface until UI Process reads m_surface. + // If m_surface exists, it was created in the previous update. + m_handle.clear(); + m_surface.clear(); +} + +static const double clearContentsTimerInterval = 3; + +void CoordinatedImageBacking::updateVisibilityIfNeeded(bool& changedToVisible) +{ + bool previousIsVisible = m_isVisible; + + m_isVisible = false; + for (size_t i = 0; i < m_hosts.size(); ++i) { + if (m_hosts[i]->imageBackingVisible()) { + m_isVisible = true; + break; + } + } + + bool changedToInvisible = previousIsVisible && !m_isVisible; + if (changedToInvisible) { + ASSERT(!m_clearContentsTimer.isActive()); + m_clearContentsTimer.startOneShot(clearContentsTimerInterval); + } + + changedToVisible = !previousIsVisible && m_isVisible; + + if (m_isVisible && m_clearContentsTimer.isActive()) { + m_clearContentsTimer.stop(); + // We don't want to update the texture if we didn't remove the texture. + changedToVisible = false; + } +} + +void CoordinatedImageBacking::clearContentsTimerFired(WebCore::Timer<CoordinatedImageBacking>*) +{ + m_coordinator->clearImageBackingContents(id()); +} + +} +#endif diff --git a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedImageBacking.h b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedImageBacking.h new file mode 100644 index 000000000..76266a4b4 --- /dev/null +++ b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedImageBacking.h @@ -0,0 +1,96 @@ +/* + * Copyright (C) 2012 Company 100, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + + +#ifndef CoordinatedImageBacking_h +#define CoordinatedImageBacking_h + +#if USE(COORDINATED_GRAPHICS) +#include "Image.h" +#include "ShareableSurface.h" +#include "WebLayerTreeInfo.h" +#include <WebCore/Timer.h> +#include <wtf/RefCounted.h> +#include <wtf/Vector.h> + +namespace WebKit { + +class CoordinatedImageBacking : public RefCounted<CoordinatedImageBacking> { +public: + class Coordinator { + public: + virtual void createImageBacking(CoordinatedImageBackingID) = 0; + virtual void updateImageBacking(CoordinatedImageBackingID, const ShareableSurface::Handle&) = 0; + virtual void clearImageBackingContents(CoordinatedImageBackingID) = 0; + virtual void removeImageBacking(CoordinatedImageBackingID) = 0; + }; + + class Host { + public: + virtual bool imageBackingVisible() = 0; + }; + + static PassRefPtr<CoordinatedImageBacking> create(Coordinator*, PassRefPtr<WebCore::Image>); + virtual ~CoordinatedImageBacking(); + + static CoordinatedImageBackingID getCoordinatedImageBackingID(WebCore::Image*); + CoordinatedImageBackingID id() const { return m_id; } + + void addHost(Host*); + void removeHost(Host*); + + // When a new image is updated or an animated gif is progressed, CoordinatedGraphicsLayer calls markDirty(). + void markDirty(); + + // Create, remove or update its backing. + void update(); + +private: + CoordinatedImageBacking(Coordinator*, PassRefPtr<WebCore::Image>); + + void releaseSurfaceIfNeeded(); + void updateVisibilityIfNeeded(bool& changedToVisible); + void clearContentsTimerFired(WebCore::Timer<CoordinatedImageBacking>*); + + Coordinator* m_coordinator; + RefPtr<WebCore::Image> m_image; + WebCore::NativeImagePtr m_nativeImagePtr; + CoordinatedImageBackingID m_id; + Vector<Host*> m_hosts; + + RefPtr<ShareableSurface> m_surface; + OwnPtr<ShareableSurface::Handle> m_handle; + + WebCore::Timer<CoordinatedImageBacking> m_clearContentsTimer; + + bool m_isDirty; + bool m_isVisible; + +}; + +} +#endif + +#endif // CoordinatedImageBacking_H diff --git a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedTile.h b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedTile.h index 32ff4e7c7..db315ad6d 100644 --- a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedTile.h +++ b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/CoordinatedTile.h @@ -88,7 +88,7 @@ public: void paintCheckerPattern(WebCore::GraphicsContext*, const WebCore::FloatRect&); private: - CoordinatedTileBackend(CoordinatedTileClient*); + explicit CoordinatedTileBackend(CoordinatedTileClient*); CoordinatedTileClient* m_client; }; diff --git a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.cpp b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.cpp index 5d9b3ef38..176dcf6e3 100644 --- a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.cpp +++ b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.cpp @@ -41,12 +41,20 @@ #include "WebPageProxyMessages.h" #include <WebCore/Frame.h> #include <WebCore/FrameView.h> +#include <WebCore/GraphicsSurface.h> #include <WebCore/Page.h> #include <WebCore/RenderLayer.h> #include <WebCore/RenderLayerBacking.h> #include <WebCore/RenderLayerCompositor.h> #include <WebCore/RenderView.h> #include <WebCore/Settings.h> +#include <WebCore/TextureMapperPlatformLayer.h> +#include <wtf/TemporaryChange.h> + +#if ENABLE(CSS_SHADERS) +#include "CustomFilterValidatedProgram.h" +#include "ValidatedCustomFilterOperation.h" +#endif using namespace WebCore; @@ -59,19 +67,24 @@ PassRefPtr<LayerTreeCoordinator> LayerTreeCoordinator::create(WebPage* webPage) LayerTreeCoordinator::~LayerTreeCoordinator() { +#if ENABLE(CSS_SHADERS) + disconnectCustomFilterPrograms(); +#endif + // Prevent setCoordinatedGraphicsLayerClient(0) -> detachLayer() from modifying the set while we iterate it. HashSet<WebCore::CoordinatedGraphicsLayer*> registeredLayers; registeredLayers.swap(m_registeredLayers); HashSet<WebCore::CoordinatedGraphicsLayer*>::iterator end = registeredLayers.end(); for (HashSet<WebCore::CoordinatedGraphicsLayer*>::iterator it = registeredLayers.begin(); it != end; ++it) - (*it)->setCoordinatedGraphicsLayerClient(0); + (*it)->setCoordinator(0); } LayerTreeCoordinator::LayerTreeCoordinator(WebPage* webPage) : LayerTreeHost(webPage) , m_notifyAfterScheduledLayerFlush(false) , m_isValid(true) + , m_isPurging(false) , m_waitingForUIProcess(true) , m_isSuspended(false) , m_contentsScale(1) @@ -96,7 +109,6 @@ LayerTreeCoordinator::LayerTreeCoordinator(WebPage* webPage) m_layerTreeContext.webLayerID = toCoordinatedGraphicsLayer(webRootLayer)->id(); m_nonCompositedContentLayer = GraphicsLayer::create(this, this); - toCoordinatedGraphicsLayer(m_rootLayer.get())->setCoordinatedGraphicsLayerClient(this); #ifndef NDEBUG m_nonCompositedContentLayer->setName("LayerTreeCoordinator non-composited content"); #endif @@ -267,7 +279,7 @@ bool LayerTreeCoordinator::flushPendingLayerChanges() m_rootLayer->flushCompositingStateForThisLayerOnly(); - purgeReleasedImages(); + flushPendingImageBackingChanges(); if (m_shouldSyncRootLayer) { m_webPage->send(Messages::LayerTreeCoordinatorProxy::SetRootCompositingLayer(toCoordinatedGraphicsLayer(m_rootLayer.get())->id())); @@ -311,10 +323,28 @@ void LayerTreeCoordinator::syncLayerChildren(WebLayerID id, const Vector<WebLaye } #if USE(GRAPHICS_SURFACE) -void LayerTreeCoordinator::syncCanvas(WebLayerID id, const IntSize& canvasSize, const GraphicsSurfaceToken& token, uint32_t frontBuffer) +void LayerTreeCoordinator::createCanvas(WebLayerID id, PlatformLayer* canvasPlatformLayer) +{ + m_shouldSyncFrame = true; + GraphicsSurfaceToken token = canvasPlatformLayer->graphicsSurfaceToken(); + IntSize canvasSize = canvasPlatformLayer->platformLayerSize(); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::CreateCanvas(id, canvasSize, token)); +} + +void LayerTreeCoordinator::syncCanvas(WebLayerID id, PlatformLayer* canvasPlatformLayer) +{ + m_shouldSyncFrame = true; + uint32_t frontBuffer = canvasPlatformLayer->copyToGraphicsSurface(); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::SyncCanvas(id, frontBuffer)); +} + +void LayerTreeCoordinator::destroyCanvas(WebLayerID id) { + if (m_isPurging) + return; + m_shouldSyncFrame = true; - m_webPage->send(Messages::LayerTreeCoordinatorProxy::SyncCanvas(id, canvasSize, token, frontBuffer)); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::DestroyCanvas(id)); } #endif @@ -322,18 +352,64 @@ void LayerTreeCoordinator::syncCanvas(WebLayerID id, const IntSize& canvasSize, void LayerTreeCoordinator::syncLayerFilters(WebLayerID id, const FilterOperations& filters) { m_shouldSyncFrame = true; +#if ENABLE(CSS_SHADERS) + checkCustomFilterProgramProxies(filters); +#endif m_webPage->send(Messages::LayerTreeCoordinatorProxy::SetCompositingLayerFilters(id, filters)); } #endif -void LayerTreeCoordinator::attachLayer(CoordinatedGraphicsLayer* layer) +#if ENABLE(CSS_SHADERS) +void LayerTreeCoordinator::checkCustomFilterProgramProxies(const FilterOperations& filters) +{ + // We need to create the WebCustomFilterProgramProxy objects before we get to serialize the + // custom filters to the other process. That's because WebCustomFilterProgramProxy needs + // to link back to the coordinator, so that we can send a message to the UI process when + // the program is not needed anymore. + // Note that the serialization will only happen at a later time in ArgumentCoder<WebCore::FilterOperations>::encode. + // At that point the program will only be serialized once. All the other times it will only use the ID of the program. + for (size_t i = 0; i < filters.size(); ++i) { + const FilterOperation* operation = filters.at(i); + if (operation->getOperationType() != FilterOperation::VALIDATED_CUSTOM) + continue; + const ValidatedCustomFilterOperation* customOperation = static_cast<const ValidatedCustomFilterOperation*>(operation); + ASSERT(customOperation->validatedProgram()->isInitialized()); + TextureMapperPlatformCompiledProgram* program = customOperation->validatedProgram()->platformCompiledProgram(); + + RefPtr<WebCustomFilterProgramProxy> customFilterProgramProxy; + if (program->client()) + customFilterProgramProxy = static_cast<WebCustomFilterProgramProxy*>(program->client()); + else { + customFilterProgramProxy = WebCustomFilterProgramProxy::create(); + program->setClient(customFilterProgramProxy); + } + + if (!customFilterProgramProxy->client()) { + customFilterProgramProxy->setClient(this); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::CreateCustomFilterProgram(customFilterProgramProxy->id(), customOperation->validatedProgram()->validatedProgramInfo())); + } else { + // If the client was not disconnected then this coordinator must be the client for it. + ASSERT(customFilterProgramProxy->client() == this); + } + } +} + +void LayerTreeCoordinator::removeCustomFilterProgramProxy(WebCustomFilterProgramProxy* customFilterProgramProxy) { - ASSERT(!m_registeredLayers.contains(layer)); - m_registeredLayers.add(layer); + // At this time the shader is not needed anymore, so we remove it from our set and + // send a message to the other process to delete it. + m_customFilterPrograms.remove(customFilterProgramProxy); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::RemoveCustomFilterProgram(customFilterProgramProxy->id())); +} - layer->setContentsScale(m_contentsScale); - layer->adjustVisibleRect(); +void LayerTreeCoordinator::disconnectCustomFilterPrograms() +{ + // Make sure that WebCore will not call into this coordinator anymore. + HashSet<WebCustomFilterProgramProxy*>::iterator iter = m_customFilterPrograms.begin(); + for (; iter != m_customFilterPrograms.end(); ++iter) + (*iter)->setClient(0); } +#endif void LayerTreeCoordinator::detachLayer(CoordinatedGraphicsLayer* layer) { @@ -447,13 +523,6 @@ void LayerTreeCoordinator::didPerformScheduledLayerFlush() } } -void LayerTreeCoordinator::purgeReleasedImages() -{ - for (size_t i = 0; i < m_releasedDirectlyCompositedImages.size(); ++i) - m_webPage->send(Messages::LayerTreeCoordinatorProxy::DestroyDirectlyCompositedImage(m_releasedDirectlyCompositedImages[i])); - m_releasedDirectlyCompositedImages.clear(); -} - void LayerTreeCoordinator::layerFlushTimerFired(Timer<LayerTreeCoordinator>*) { performScheduledLayerFlush(); @@ -481,79 +550,55 @@ void LayerTreeCoordinator::destroyPageOverlayLayer() m_pageOverlayLayer = nullptr; } -int64_t LayerTreeCoordinator::adoptImageBackingStore(Image* image) +PassRefPtr<CoordinatedImageBacking> LayerTreeCoordinator::createImageBackingIfNeeded(Image* image) { - if (!image) - return InvalidWebLayerID; - - int64_t key = 0; - -#if PLATFORM(QT) - QPixmap* nativeImage = image->nativeImageForCurrentFrame(); - - if (!nativeImage) - return InvalidWebLayerID; - - key = nativeImage->cacheKey(); -#elif USE(CAIRO) - NativeImageCairo* nativeImage = image->nativeImageForCurrentFrame(); - if (!nativeImage) - return InvalidWebLayerID; - // This can be safely done since we own the reference. - // A corresponding cairo_surface_destroy() is ensured in releaseImageBackingStore(). - cairo_surface_t* cairoSurface = cairo_surface_reference(nativeImage->surface()); - key = reinterpret_cast<int64_t>(cairoSurface); -#endif - - HashMap<int64_t, int>::iterator it = m_directlyCompositedImageRefCounts.find(key); - - if (it != m_directlyCompositedImageRefCounts.end()) { - ++(it->value); - return key; - } - - // Check if we were going to release this image during the next flush. - size_t releasedIndex = m_releasedDirectlyCompositedImages.find(key); - if (releasedIndex == notFound) { - RefPtr<ShareableBitmap> bitmap = ShareableBitmap::createShareable(image->size(), (image->currentFrameHasAlpha() ? ShareableBitmap::SupportsAlpha : 0)); - { - OwnPtr<WebCore::GraphicsContext> graphicsContext = bitmap->createGraphicsContext(); - graphicsContext->drawImage(image, ColorSpaceDeviceRGB, IntPoint::zero()); - } - ShareableBitmap::Handle handle; - bitmap->createHandle(handle); - m_webPage->send(Messages::LayerTreeCoordinatorProxy::CreateDirectlyCompositedImage(key, handle)); + CoordinatedImageBackingID imageID = CoordinatedImageBacking::getCoordinatedImageBackingID(image); + ImageBackingMap::iterator it = m_imageBackings.find(imageID); + RefPtr<CoordinatedImageBacking> imageBacking; + if (it == m_imageBackings.end()) { + imageBacking = CoordinatedImageBacking::create(this, image); + m_imageBackings.add(imageID, imageBacking); } else - m_releasedDirectlyCompositedImages.remove(releasedIndex); + imageBacking = it->value; - m_directlyCompositedImageRefCounts.add(key, 1); - return key; + return imageBacking; } -void LayerTreeCoordinator::releaseImageBackingStore(int64_t key) +void LayerTreeCoordinator::createImageBacking(CoordinatedImageBackingID imageID) { - if (!key) - return; - HashMap<int64_t, int>::iterator it = m_directlyCompositedImageRefCounts.find(key); - if (it == m_directlyCompositedImageRefCounts.end()) - return; + m_shouldSyncFrame = true; + m_webPage->send(Messages::LayerTreeCoordinatorProxy::CreateImageBacking(imageID)); +} + +void LayerTreeCoordinator::updateImageBacking(CoordinatedImageBackingID imageID, const ShareableSurface::Handle& handle) +{ + m_shouldSyncFrame = true; + m_webPage->send(Messages::LayerTreeCoordinatorProxy::UpdateImageBacking(imageID, handle)); +} - it->value--; +void LayerTreeCoordinator::clearImageBackingContents(CoordinatedImageBackingID imageID) +{ + m_shouldSyncFrame = true; + m_webPage->send(Messages::LayerTreeCoordinatorProxy::ClearImageBackingContents(imageID)); +} - if (it->value) +void LayerTreeCoordinator::removeImageBacking(CoordinatedImageBackingID imageID) +{ + if (m_isPurging) return; -#if USE(CAIRO) - // Complement the referencing in adoptImageBackingStore(). - cairo_surface_t* cairoSurface = reinterpret_cast<cairo_surface_t*>(key); - cairo_surface_destroy(cairoSurface); -#endif - - m_directlyCompositedImageRefCounts.remove(it); - m_releasedDirectlyCompositedImages.append(key); - scheduleLayerFlush(); + ASSERT(m_imageBackings.contains(imageID)); + m_shouldSyncFrame = true; + m_imageBackings.remove(imageID); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::RemoveImageBacking(imageID)); } +void LayerTreeCoordinator::flushPendingImageBackingChanges() +{ + ImageBackingMap::iterator end = m_imageBackings.end(); + for (ImageBackingMap::iterator iter = m_imageBackings.begin(); iter != end; ++iter) + iter->value->update(); +} void LayerTreeCoordinator::notifyAnimationStarted(const WebCore::GraphicsLayer*, double /* time */) { @@ -580,9 +625,12 @@ void LayerTreeCoordinator::paintContents(const WebCore::GraphicsLayer* graphicsL PassOwnPtr<GraphicsLayer> LayerTreeCoordinator::createGraphicsLayer(GraphicsLayerClient* client) { - CoordinatedGraphicsLayer* newLayer = new CoordinatedGraphicsLayer(client); - newLayer->setCoordinatedGraphicsLayerClient(this); - return adoptPtr(newLayer); + CoordinatedGraphicsLayer* layer = new CoordinatedGraphicsLayer(client); + layer->setCoordinator(this); + m_registeredLayers.add(layer); + layer->setContentsScale(m_contentsScale); + layer->adjustVisibleRect(); + return adoptPtr(layer); } bool LayerTreeHost::supportsAcceleratedCompositing() @@ -590,20 +638,22 @@ bool LayerTreeHost::supportsAcceleratedCompositing() return true; } -void LayerTreeCoordinator::createTile(WebLayerID layerID, int tileID, const SurfaceUpdateInfo& updateInfo, const WebCore::IntRect& targetRect) +void LayerTreeCoordinator::createTile(WebLayerID layerID, int tileID, const SurfaceUpdateInfo& updateInfo, const WebCore::IntRect& tileRect) { m_shouldSyncFrame = true; - m_webPage->send(Messages::LayerTreeCoordinatorProxy::CreateTileForLayer(layerID, tileID, targetRect, updateInfo)); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::CreateTileForLayer(layerID, tileID, tileRect, updateInfo)); } -void LayerTreeCoordinator::updateTile(WebLayerID layerID, int tileID, const SurfaceUpdateInfo& updateInfo, const WebCore::IntRect& targetRect) +void LayerTreeCoordinator::updateTile(WebLayerID layerID, int tileID, const SurfaceUpdateInfo& updateInfo, const WebCore::IntRect& tileRect) { m_shouldSyncFrame = true; - m_webPage->send(Messages::LayerTreeCoordinatorProxy::UpdateTileForLayer(layerID, tileID, targetRect, updateInfo)); + m_webPage->send(Messages::LayerTreeCoordinatorProxy::UpdateTileForLayer(layerID, tileID, tileRect, updateInfo)); } void LayerTreeCoordinator::removeTile(WebLayerID layerID, int tileID) { + if (m_isPurging) + return; m_shouldSyncFrame = true; m_webPage->send(Messages::LayerTreeCoordinatorProxy::RemoveTileForLayer(layerID, tileID)); } @@ -615,6 +665,8 @@ void LayerTreeCoordinator::createUpdateAtlas(int atlasID, const ShareableSurface void LayerTreeCoordinator::removeUpdateAtlas(int atlasID) { + if (m_isPurging) + return; m_webPage->send(Messages::LayerTreeCoordinatorProxy::RemoveUpdateAtlas(atlasID)); } @@ -627,7 +679,19 @@ WebCore::IntRect LayerTreeCoordinator::visibleContentsRect() const void LayerTreeCoordinator::setLayerAnimations(WebLayerID layerID, const GraphicsLayerAnimations& animations) { m_shouldSyncFrame = true; - m_webPage->send(Messages::LayerTreeCoordinatorProxy::SetLayerAnimations(layerID, animations.getActiveAnimations())); + GraphicsLayerAnimations activeAnimations = animations.getActiveAnimations(); +#if ENABLE(CSS_SHADERS) + for (size_t i = 0; i < activeAnimations.animations().size(); ++i) { + const KeyframeValueList& keyframes = animations.animations().at(i).keyframes(); + if (keyframes.property() != AnimatedPropertyWebkitFilter) + continue; + for (size_t j = 0; j < keyframes.size(); ++j) { + const FilterAnimationValue* filterValue = static_cast<const FilterAnimationValue*>(keyframes.at(i)); + checkCustomFilterProgramProxies(*filterValue->value()); + } + } +#endif + m_webPage->send(Messages::LayerTreeCoordinatorProxy::SetLayerAnimations(layerID, activeAnimations)); } void LayerTreeCoordinator::setVisibleContentsRect(const IntRect& rect, float scale, const FloatPoint& trajectoryVector) @@ -690,14 +754,13 @@ bool LayerTreeCoordinator::layerTreeTileUpdatesAllowed() const void LayerTreeCoordinator::purgeBackingStores() { + TemporaryChange<bool> purgingToggle(m_isPurging, true); + HashSet<WebCore::CoordinatedGraphicsLayer*>::iterator end = m_registeredLayers.end(); for (HashSet<WebCore::CoordinatedGraphicsLayer*>::iterator it = m_registeredLayers.begin(); it != end; ++it) (*it)->purgeBackingStores(); - purgeReleasedImages(); - - ASSERT(!m_directlyCompositedImageRefCounts.size()); - ASSERT(!m_releasedDirectlyCompositedImages.size()); + m_imageBackings.clear(); m_updateAtlases.clear(); } @@ -753,5 +816,10 @@ void LayerTreeCoordinator::releaseInactiveAtlasesTimerFired(Timer<LayerTreeCoord m_releaseInactiveAtlasesTimer.stop(); } +void LayerTreeCoordinator::setBackgroundColor(const WebCore::Color& color) +{ + m_webPage->send(Messages::LayerTreeCoordinatorProxy::SetBackgroundColor(color)); +} + } // namespace WebKit #endif // USE(COORDINATED_GRAPHICS) diff --git a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.h b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.h index cacb68eaa..f04b50821 100644 --- a/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.h +++ b/Source/WebKit2/WebProcess/WebPage/CoordinatedGraphics/LayerTreeCoordinator.h @@ -23,15 +23,19 @@ #if USE(COORDINATED_GRAPHICS) #include "CoordinatedGraphicsLayer.h" +#include "CoordinatedImageBacking.h" #include "LayerTreeContext.h" #include "LayerTreeHost.h" #include "Timer.h" #include "UpdateAtlas.h" #include <WebCore/GraphicsLayerClient.h> #include <WebCore/GraphicsLayerFactory.h> -#include <WebCore/GraphicsSurface.h> #include <wtf/OwnPtr.h> +#if ENABLE(CSS_SHADERS) +#include "WebCustomFilterProgramProxy.h" +#endif + namespace WebKit { class UpdateInfo; @@ -39,8 +43,13 @@ class WebPage; class LayerTreeCoordinator : public LayerTreeHost, WebCore::GraphicsLayerClient , public CoordinatedGraphicsLayerClient + , public CoordinatedImageBacking::Coordinator , public UpdateAtlasClient - , public WebCore::GraphicsLayerFactory { + , public WebCore::GraphicsLayerFactory +#if ENABLE(CSS_SHADERS) + , WebCustomFilterProgramProxyClient +#endif +{ public: static PassRefPtr<LayerTreeCoordinator> create(WebPage*); virtual ~LayerTreeCoordinator(); @@ -67,8 +76,7 @@ public: virtual void pauseRendering() { m_isSuspended = true; } virtual void resumeRendering() { m_isSuspended = false; scheduleLayerFlush(); } virtual void deviceScaleFactorDidChange() { } - virtual int64_t adoptImageBackingStore(WebCore::Image*); - virtual void releaseImageBackingStore(int64_t); + virtual PassRefPtr<CoordinatedImageBacking> createImageBackingIfNeeded(WebCore::Image*) OVERRIDE; virtual void createTile(WebLayerID, int tileID, const SurfaceUpdateInfo&, const WebCore::IntRect&); virtual void updateTile(WebLayerID, int tileID, const SurfaceUpdateInfo&, const WebCore::IntRect&); @@ -88,9 +96,10 @@ public: virtual void syncLayerFilters(WebLayerID, const WebCore::FilterOperations&); #endif #if USE(GRAPHICS_SURFACE) - virtual void syncCanvas(WebLayerID, const WebCore::IntSize& canvasSize, const WebCore::GraphicsSurfaceToken&, uint32_t frontBuffer) OVERRIDE; + virtual void createCanvas(WebLayerID, WebCore::PlatformLayer*) OVERRIDE; + virtual void syncCanvas(WebLayerID, WebCore::PlatformLayer*) OVERRIDE; + virtual void destroyCanvas(WebLayerID) OVERRIDE; #endif - virtual void attachLayer(WebCore::CoordinatedGraphicsLayer*); virtual void detachLayer(WebCore::CoordinatedGraphicsLayer*); virtual void syncFixedLayers(); @@ -103,6 +112,7 @@ public: #if ENABLE(REQUEST_ANIMATION_FRAME) virtual void scheduleAnimation() OVERRIDE; #endif + virtual void setBackgroundColor(const WebCore::Color&) OVERRIDE; protected: explicit LayerTreeCoordinator(WebPage*); @@ -113,6 +123,14 @@ private: virtual void notifyFlushRequired(const WebCore::GraphicsLayer*); virtual void paintContents(const WebCore::GraphicsLayer*, WebCore::GraphicsContext&, WebCore::GraphicsLayerPaintingPhase, const WebCore::IntRect& clipRect); + // CoordinatedImageBacking::Coordinator + virtual void createImageBacking(CoordinatedImageBackingID) OVERRIDE; + virtual void updateImageBacking(CoordinatedImageBackingID, const ShareableSurface::Handle&) OVERRIDE; + virtual void clearImageBackingContents(CoordinatedImageBackingID) OVERRIDE; + virtual void removeImageBacking(CoordinatedImageBackingID) OVERRIDE; + + void flushPendingImageBackingChanges(); + // GraphicsLayerFactory virtual PassOwnPtr<WebCore::GraphicsLayer> createGraphicsLayer(WebCore::GraphicsLayerClient*) OVERRIDE; @@ -126,7 +144,6 @@ private: void syncDisplayState(); void lockAnimations(); void unlockAnimations(); - void purgeReleasedImages(); void layerFlushTimerFired(WebCore::Timer<LayerTreeCoordinator>*); @@ -137,6 +154,14 @@ private: void releaseInactiveAtlasesTimerFired(WebCore::Timer<LayerTreeCoordinator>*); +#if ENABLE(CSS_SHADERS) + // WebCustomFilterProgramProxyClient + void removeCustomFilterProgramProxy(WebCustomFilterProgramProxy*); + + void checkCustomFilterProgramProxies(const WebCore::FilterOperations&); + void disconnectCustomFilterPrograms(); +#endif + OwnPtr<WebCore::GraphicsLayer> m_rootLayer; // The layer which contains all non-composited content. @@ -147,12 +172,18 @@ private: HashSet<WebCore::CoordinatedGraphicsLayer*> m_registeredLayers; Vector<WebLayerID> m_detachedLayers; - HashMap<int64_t, int> m_directlyCompositedImageRefCounts; - Vector<int64_t> m_releasedDirectlyCompositedImages; + typedef HashMap<CoordinatedImageBackingID, RefPtr<CoordinatedImageBacking> > ImageBackingMap; + ImageBackingMap m_imageBackings; Vector<OwnPtr<UpdateAtlas> > m_updateAtlases; +#if ENABLE(CSS_SHADERS) + HashSet<WebCustomFilterProgramProxy*> m_customFilterPrograms; +#endif + bool m_notifyAfterScheduledLayerFlush; bool m_isValid; + // We don't send the messages related to releasing resources to UI Process during purging, because UI Process already had removed all resources. + bool m_isPurging; bool m_waitingForUIProcess; bool m_isSuspended; diff --git a/Source/WebKit2/WebProcess/WebPage/LayerTreeHost.h b/Source/WebKit2/WebProcess/WebPage/LayerTreeHost.h index 7a1ca6cf6..a29983ed2 100644 --- a/Source/WebKit2/WebProcess/WebPage/LayerTreeHost.h +++ b/Source/WebKit2/WebProcess/WebPage/LayerTreeHost.h @@ -27,6 +27,7 @@ #define LayerTreeHost_h #include "LayerTreeContext.h" +#include <WebCore/Color.h> #include <wtf/PassRefPtr.h> #include <wtf/RefCounted.h> @@ -88,6 +89,7 @@ public: virtual void resumeRendering() { } virtual WebCore::GraphicsLayerFactory* graphicsLayerFactory() { return 0; } + virtual void setBackgroundColor(const WebCore::Color&) { } #if USE(COORDINATED_GRAPHICS) virtual void setVisibleContentsRect(const WebCore::IntRect&, float /* scale */, const WebCore::FloatPoint&) { } diff --git a/Source/WebKit2/WebProcess/WebPage/WebContextMenu.cpp b/Source/WebKit2/WebProcess/WebPage/WebContextMenu.cpp index 3a91d90b7..3273bdc09 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebContextMenu.cpp +++ b/Source/WebKit2/WebProcess/WebPage/WebContextMenu.cpp @@ -59,10 +59,7 @@ void WebContextMenu::show() ContextMenu* menu = controller->contextMenu(); if (!menu) return; - Node* node = controller->hitTestResult().innerNonSharedNode(); - if (!node) - return; - Frame* frame = node->document()->frame(); + Frame* frame = controller->hitTestResult().innerNodeFrame(); if (!frame) return; FrameView* view = frame->view(); @@ -86,7 +83,7 @@ void WebContextMenu::show() // Mark the WebPage has having a shown context menu then notify the UIProcess. m_page->contextMenuShowing(); - m_page->send(Messages::WebPageProxy::ShowContextMenu(view->contentsToWindow(controller->hitTestResult().roundedPoint()), webHitTestResultData, proposedMenu, InjectedBundleUserMessageEncoder(userData.get()))); + m_page->send(Messages::WebPageProxy::ShowContextMenu(view->contentsToWindow(controller->hitTestResult().roundedPointInInnerNodeFrame()), webHitTestResultData, proposedMenu, InjectedBundleUserMessageEncoder(userData.get()))); } void WebContextMenu::itemSelected(const WebContextMenuItemData& item) diff --git a/Source/WebKit2/WebProcess/WebPage/WebFrame.cpp b/Source/WebKit2/WebProcess/WebPage/WebFrame.cpp index 6840914b4..c65c5e5bc 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebFrame.cpp +++ b/Source/WebKit2/WebProcess/WebPage/WebFrame.cpp @@ -31,6 +31,7 @@ #include "InjectedBundleNodeHandle.h" #include "InjectedBundleRangeHandle.h" #include "InjectedBundleScriptWorld.h" +#include "PluginView.h" #include "WKAPICast.h" #include "WKBundleAPICast.h" #include "WebChromeClient.h" @@ -54,6 +55,7 @@ #include <WebCore/JSElement.h> #include <WebCore/JSRange.h> #include <WebCore/Page.h> +#include <WebCore/PluginDocument.h> #include <WebCore/RenderTreeAsText.h> #include <WebCore/ResourceBuffer.h> #include <WebCore/SecurityOrigin.h> @@ -544,6 +546,17 @@ JSGlobalContextRef WebFrame::jsContextForWorld(InjectedBundleScriptWorld* world) return toGlobalRef(m_coreFrame->script()->globalObject(world->coreWorld())->globalExec()); } +bool WebFrame::handlesPageScaleGesture() const +{ + if (!m_coreFrame->document()->isPluginDocument()) + return 0; + + PluginDocument* pluginDocument = static_cast<PluginDocument*>(m_coreFrame->document()); + PluginView* pluginView = static_cast<PluginView*>(pluginDocument->pluginWidget()); + + return pluginView->handlesPageScaleFactor(); +} + IntRect WebFrame::contentBounds() const { if (!m_coreFrame) diff --git a/Source/WebKit2/WebProcess/WebPage/WebFrame.h b/Source/WebKit2/WebProcess/WebPage/WebFrame.h index a719e2447..f606567a0 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebFrame.h +++ b/Source/WebKit2/WebProcess/WebPage/WebFrame.h @@ -117,6 +117,7 @@ public: bool getDocumentBackgroundColor(double* red, double* green, double* blue, double* alpha); bool containsAnyFormElements() const; void stopLoading(); + bool handlesPageScaleGesture() const; static WebFrame* frameForContext(JSContextRef); diff --git a/Source/WebKit2/WebProcess/WebPage/WebInspector.cpp b/Source/WebKit2/WebProcess/WebPage/WebInspector.cpp index 7fa40e14f..02a659be5 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebInspector.cpp +++ b/Source/WebKit2/WebProcess/WebPage/WebInspector.cpp @@ -143,6 +143,12 @@ void WebInspector::close() m_page->corePage()->inspectorController()->close(); } +void WebInspector::setAttachedWindow(bool attached) +{ + if (m_frontendClient) + m_frontendClient->setAttachedWindow(attached); +} + void WebInspector::evaluateScriptForTest(long callID, const String& script) { m_page->corePage()->inspectorController()->evaluateForTestInFrontend(callID, script); @@ -236,8 +242,12 @@ void WebInspector::stopPageProfiling() void WebInspector::updateDockingAvailability() { - if (m_frontendClient) - m_frontendClient->setDockingUnavailable(!m_frontendClient->canAttachWindow()); + if (!m_frontendClient) + return; + + bool canAttachWindow = m_frontendClient->canAttachWindow(); + WebProcess::shared().connection()->send(Messages::WebInspectorProxy::AttachAvailabilityChanged(canAttachWindow), m_page->pageID()); + m_frontendClient->setDockingUnavailable(!canAttachWindow); } #if ENABLE(INSPECTOR_SERVER) diff --git a/Source/WebKit2/WebProcess/WebPage/WebInspector.h b/Source/WebKit2/WebProcess/WebPage/WebInspector.h index 2f1047589..54bddfc3a 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebInspector.h +++ b/Source/WebKit2/WebProcess/WebPage/WebInspector.h @@ -59,6 +59,8 @@ public: void show(); void close(); + void setAttachedWindow(bool); + void evaluateScriptForTest(long callID, const String& script); void setJavaScriptProfilingEnabled(bool); diff --git a/Source/WebKit2/WebProcess/WebPage/WebInspector.messages.in b/Source/WebKit2/WebProcess/WebPage/WebInspector.messages.in index 998272d9f..20ee989fa 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebInspector.messages.in +++ b/Source/WebKit2/WebProcess/WebPage/WebInspector.messages.in @@ -25,6 +25,7 @@ messages -> WebInspector { Show() Close() + SetAttachedWindow(bool attached) ShowConsole() ShowResources() ShowMainResourceForFrame(uint64_t frameID) diff --git a/Source/WebKit2/WebProcess/WebPage/WebPage.cpp b/Source/WebKit2/WebProcess/WebPage/WebPage.cpp index 60ca6781a..c91c73ed1 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebPage.cpp +++ b/Source/WebKit2/WebProcess/WebPage/WebPage.cpp @@ -60,6 +60,7 @@ #include "WebEvent.h" #include "WebEventConversion.h" #include "WebFrame.h" +#include "WebFrameNetworkingContext.h" #include "WebFullScreenManager.h" #include "WebFullScreenManagerMessages.h" #include "WebGeolocationClient.h" @@ -276,6 +277,7 @@ WebPage::WebPage(uint64_t pageID, const WebPageCreationParameters& parameters) , m_visibilityState(WebCore::PageVisibilityStateVisible) #endif , m_inspectorClient(0) + , m_backgroundColor(Color::white) { ASSERT(m_pageID); // FIXME: This is a non-ideal location for this Setting and @@ -1021,6 +1023,7 @@ void WebPage::sendViewportAttributesChanged() int deviceHeight = (settings->deviceHeight() > 0) ? settings->deviceHeight() : m_viewportSize.height(); ViewportAttributes attr = computeViewportAttributes(m_page->viewportArguments(), minimumLayoutFallbackWidth, deviceWidth, deviceHeight, m_page->deviceScaleFactor(), m_viewportSize); + attr.initialScale = m_page->viewportArguments().zoom; // Resets auto (-1) if no value was set by user. // This also takes care of the relayout. setFixedLayoutSize(IntSize(static_cast<int>(attr.layoutSize.width()), static_cast<int>(attr.layoutSize.height()))); @@ -1034,7 +1037,7 @@ void WebPage::setViewportSize(const IntSize& size) if (m_viewportSize == size) return; - m_viewportSize = size; + m_viewportSize = size; sendViewportAttributesChanged(); } @@ -1695,17 +1698,21 @@ void WebPage::highlightPotentialActivation(const IntPoint& point, const IntSize& #endif // Find the node to highlight. This is not the same as the node responding the tap gesture, because many // pages has a global click handler and we do not want to highlight the body. - // Instead find the enclosing link or focusable element, or the last enclosing inline element. for (Node* node = adjustedNode; node; node = node->parentOrHostNode()) { if (node->isDocumentNode() || node->isFrameOwnerElement()) break; - if (node->isMouseFocusable() || node->willRespondToMouseClickEvents()) { + + // We always highlight focusable (form-elements), image links or content-editable elements. + if (node->isMouseFocusable() || node->isLink() || node->isContentEditable()) activationNode = node; - break; + else if (node->willRespondToMouseClickEvents()) { + // Highlight elements with default mouse-click handlers, but highlight only inline elements with + // scripted event-handlers. + if (!node->Node::willRespondToMouseClickEvents() || (node->renderer() && node->renderer()->isInline())) + activationNode = node; } - if (node->renderer() && node->renderer()->isInline()) - activationNode = node; - else if (activationNode) + + if (activationNode) break; } @@ -2174,7 +2181,16 @@ void WebPage::updatePreferences(const WebPreferencesStore& store) settings->setLocalStorageEnabled(store.getBoolValueForKey(WebPreferencesKey::localStorageEnabledKey())); settings->setXSSAuditorEnabled(store.getBoolValueForKey(WebPreferencesKey::xssAuditorEnabledKey())); settings->setFrameFlatteningEnabled(store.getBoolValueForKey(WebPreferencesKey::frameFlatteningEnabledKey())); - settings->setPrivateBrowsingEnabled(store.getBoolValueForKey(WebPreferencesKey::privateBrowsingEnabledKey())); + + bool privateBrowsingEnabled = store.getBoolValueForKey(WebPreferencesKey::privateBrowsingEnabledKey()); +#if (PLATFORM(MAC) || USE(CFNETWORK)) && !PLATFORM(WIN) + if (privateBrowsingEnabled) + WebFrameNetworkingContext::ensurePrivateBrowsingSession(); + else + WebFrameNetworkingContext::destroyPrivateBrowsingSession(); +#endif + settings->setPrivateBrowsingEnabled(privateBrowsingEnabled); + settings->setDeveloperExtrasEnabled(store.getBoolValueForKey(WebPreferencesKey::developerExtrasEnabledKey())); settings->setJavaScriptExperimentsEnabled(store.getBoolValueForKey(WebPreferencesKey::javaScriptExperimentsEnabledKey())); settings->setTextAreasAreResizable(store.getBoolValueForKey(WebPreferencesKey::textAreasAreResizableKey())); @@ -2763,6 +2779,18 @@ void WebPage::mainFrameDidLayout() send(Messages::WebPageProxy::DidChangePageCount(pageCount)); m_cachedPageCount = pageCount; } + +#if USE(TILED_BACKING_STORE) && USE(ACCELERATED_COMPOSITING) + if (m_drawingArea && m_drawingArea->layerTreeHost()) { + double red, green, blue, alpha; + m_mainFrame->getDocumentBackgroundColor(&red, &green, &blue, &alpha); + RGBA32 rgba = makeRGBA32FromFloats(red, green, blue, alpha); + if (m_backgroundColor.rgb() != rgba) { + m_backgroundColor.setRGB(rgba); + m_drawingArea->layerTreeHost()->setBackgroundColor(m_backgroundColor); + } + } +#endif } void WebPage::addPluginView(PluginView* pluginView) diff --git a/Source/WebKit2/WebProcess/WebPage/WebPage.h b/Source/WebKit2/WebProcess/WebPage/WebPage.h index 606ada8a1..19af39c6e 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebPage.h +++ b/Source/WebKit2/WebProcess/WebPage/WebPage.h @@ -945,6 +945,7 @@ private: WebInspectorClient* m_inspectorClient; HashSet<String, CaseFoldingHash> m_mimeTypesWithCustomRepresentations; + WebCore::Color m_backgroundColor; }; } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebPage/gtk/WebPageAccessibilityObject.h b/Source/WebKit2/WebProcess/WebPage/atk/WebPageAccessibilityObject.h index 1b79d9bb8..1b79d9bb8 100644 --- a/Source/WebKit2/WebProcess/WebPage/gtk/WebPageAccessibilityObject.h +++ b/Source/WebKit2/WebProcess/WebPage/atk/WebPageAccessibilityObject.h diff --git a/Source/WebKit2/WebProcess/WebPage/gtk/WebPageAccessibilityObject.cpp b/Source/WebKit2/WebProcess/WebPage/atk/WebPageAccessibilityObjectAtk.cpp index 223700032..dea228bbd 100644 --- a/Source/WebKit2/WebProcess/WebPage/gtk/WebPageAccessibilityObject.cpp +++ b/Source/WebKit2/WebProcess/WebPage/atk/WebPageAccessibilityObjectAtk.cpp @@ -45,23 +45,23 @@ static AtkObject* accessibilityRootObjectWrapper(AtkObject* atkObject) if (!accessible->m_page) return 0; - Page* page = accessible->m_page->corePage(); - if (!page) + Page* corePage = accessible->m_page->corePage(); + if (!corePage) return 0; - Frame* core = page->mainFrame(); - if (!core || !core->document()) + Frame* coreFrame = corePage->mainFrame(); + if (!coreFrame || !coreFrame->document()) return 0; - AccessibilityObject* root = core->document()->axObjectCache()->rootObject(); - if (!root) + AccessibilityObject* coreRootObject = coreFrame->document()->axObjectCache()->rootObject(); + if (!coreRootObject) return 0; - AtkObject* axRoot = root->wrapper(); - if (!axRoot || !ATK_IS_OBJECT(axRoot)) + AtkObject* rootObject = coreRootObject->wrapper(); + if (!rootObject || !ATK_IS_OBJECT(rootObject)) return 0; - return axRoot; + return rootObject; } static void webPageAccessibilityObjectInitialize(AtkObject* atkObject, gpointer data) diff --git a/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.h b/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.h index 7b274a44a..c65cd65d3 100644 --- a/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.h +++ b/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.h @@ -30,21 +30,48 @@ namespace WebKit { -class RemoteLayerTreeController; +class RemoteLayerTreeContext; class RemoteGraphicsLayer : public WebCore::GraphicsLayer { public: - static PassOwnPtr<WebCore::GraphicsLayer> create(WebCore::GraphicsLayerClient*, RemoteLayerTreeController*); + static PassOwnPtr<WebCore::GraphicsLayer> create(WebCore::GraphicsLayerClient*, RemoteLayerTreeContext*); virtual ~RemoteGraphicsLayer(); + uint64_t layerID() const { return m_layerID; } + private: - RemoteGraphicsLayer(WebCore::GraphicsLayerClient*, RemoteLayerTreeController*); + RemoteGraphicsLayer(WebCore::GraphicsLayerClient*, RemoteLayerTreeContext*); // WebCore::GraphicsLayer + virtual void setName(const String&) OVERRIDE; + + virtual bool setChildren(const Vector<WebCore::GraphicsLayer*>&); + virtual void addChild(WebCore::GraphicsLayer*); + virtual void addChildAtIndex(WebCore::GraphicsLayer*, int index); + virtual void addChildAbove(WebCore::GraphicsLayer* childLayer, WebCore::GraphicsLayer* sibling); + virtual void addChildBelow(WebCore::GraphicsLayer* childLayer, WebCore::GraphicsLayer* sibling); + virtual bool replaceChild(WebCore::GraphicsLayer* oldChild, WebCore::GraphicsLayer* newChild); + + virtual void removeFromParent() OVERRIDE; + + virtual void setPosition(const WebCore::FloatPoint&) OVERRIDE; + virtual void setSize(const WebCore::FloatSize&) OVERRIDE; + virtual void setNeedsDisplay() OVERRIDE; virtual void setNeedsDisplayInRect(const WebCore::FloatRect&) OVERRIDE; + virtual void flushCompositingState(const WebCore::FloatRect&) OVERRIDE; + virtual void flushCompositingStateForThisLayerOnly() OVERRIDE; + + virtual void willBeDestroyed() OVERRIDE; + + void noteLayerPropertiesChanged(unsigned layerChanges); + void noteSublayersChanged(); + + void recursiveCommitChanges(); - RemoteLayerTreeController* m_controller; + uint64_t m_layerID; + RemoteLayerTreeContext* m_context; + unsigned m_uncommittedLayerChanges; }; } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.mm b/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.mm index 83a67c689..b2ea76325 100644 --- a/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.mm +++ b/Source/WebKit2/WebProcess/WebPage/mac/RemoteGraphicsLayer.mm @@ -26,26 +26,114 @@ #include "config.h" #include "RemoteGraphicsLayer.h" +#include "RemoteLayerTreeContext.h" +#include "RemoteLayerTreeTransaction.h" + +#include <wtf/text/CString.h> + using namespace WebCore; namespace WebKit { -PassOwnPtr<GraphicsLayer> RemoteGraphicsLayer::create(GraphicsLayerClient* client, RemoteLayerTreeController* controller) +static uint64_t generateLayerID() +{ + static uint64_t layerID; + return ++layerID; +} + +PassOwnPtr<GraphicsLayer> RemoteGraphicsLayer::create(GraphicsLayerClient* client, RemoteLayerTreeContext* context) { - return adoptPtr(new RemoteGraphicsLayer(client, controller)); + return adoptPtr(new RemoteGraphicsLayer(client, context)); } -RemoteGraphicsLayer::RemoteGraphicsLayer(GraphicsLayerClient* client, RemoteLayerTreeController* controller) +RemoteGraphicsLayer::RemoteGraphicsLayer(GraphicsLayerClient* client, RemoteLayerTreeContext* context) : GraphicsLayer(client) - , m_controller(controller) + , m_layerID(generateLayerID()) + , m_context(context) + , m_uncommittedLayerChanges(RemoteLayerTreeTransaction::NoChange) { - // FIXME: This is in place to silence a compiler warning. Remove this - // once we actually start using m_controller. - (void)m_controller; } RemoteGraphicsLayer::~RemoteGraphicsLayer() { + willBeDestroyed(); +} + +void RemoteGraphicsLayer::setName(const String& name) +{ + String longName = String::format("RemoteGraphicsLayer(%p) ", this) + name; + GraphicsLayer::setName(longName); + + noteLayerPropertiesChanged(RemoteLayerTreeTransaction::NameChanged); +} + +bool RemoteGraphicsLayer::setChildren(const Vector<GraphicsLayer*>& children) +{ + if (GraphicsLayer::setChildren(children)) { + noteSublayersChanged(); + return true; + } + + return false; +} + +void RemoteGraphicsLayer::addChild(GraphicsLayer* childLayer) +{ + GraphicsLayer::addChild(childLayer); + noteSublayersChanged(); +} + +void RemoteGraphicsLayer::addChildAtIndex(GraphicsLayer* childLayer, int index) +{ + GraphicsLayer::addChildAtIndex(childLayer, index); + noteSublayersChanged(); +} + +void RemoteGraphicsLayer::addChildAbove(GraphicsLayer* childLayer, GraphicsLayer* sibling) +{ + GraphicsLayer::addChildAbove(childLayer, sibling); + noteSublayersChanged(); +} + +void RemoteGraphicsLayer::addChildBelow(GraphicsLayer* childLayer, GraphicsLayer* sibling) +{ + GraphicsLayer::addChildBelow(childLayer, sibling); + noteSublayersChanged(); +} + +bool RemoteGraphicsLayer::replaceChild(GraphicsLayer* oldChild, GraphicsLayer* newChild) +{ + if (GraphicsLayer::replaceChild(oldChild, newChild)) { + noteSublayersChanged(); + return true; + } + + return false; +} + +void RemoteGraphicsLayer::removeFromParent() +{ + if (m_parent) + static_cast<RemoteGraphicsLayer*>(m_parent)->noteSublayersChanged(); + GraphicsLayer::removeFromParent(); +} + +void RemoteGraphicsLayer::setPosition(const FloatPoint& position) +{ + if (position == m_position) + return; + + GraphicsLayer::setPosition(position); + noteLayerPropertiesChanged(RemoteLayerTreeTransaction::PositionChanged); +} + +void RemoteGraphicsLayer::setSize(const FloatSize& size) +{ + if (size == m_size) + return; + + GraphicsLayer::setSize(size); + noteLayerPropertiesChanged(RemoteLayerTreeTransaction::SizeChanged); } void RemoteGraphicsLayer::setNeedsDisplay() @@ -60,4 +148,49 @@ void RemoteGraphicsLayer::setNeedsDisplayInRect(const FloatRect&) // FIXME: Implement this. } +void RemoteGraphicsLayer::flushCompositingState(const FloatRect&) +{ + recursiveCommitChanges(); +} + +void RemoteGraphicsLayer::flushCompositingStateForThisLayerOnly() +{ + if (!m_uncommittedLayerChanges) + return; + + m_context->currentTransaction().layerPropertiesChanged(this, m_uncommittedLayerChanges); + + m_uncommittedLayerChanges = RemoteLayerTreeTransaction::NoChange; +} + +void RemoteGraphicsLayer::willBeDestroyed() +{ + m_context->layerWillBeDestroyed(this); + GraphicsLayer::willBeDestroyed(); +} + +void RemoteGraphicsLayer::noteLayerPropertiesChanged(unsigned layerChanges) +{ + if (!m_uncommittedLayerChanges && m_client) + m_client->notifyFlushRequired(this); + m_uncommittedLayerChanges |= layerChanges; +} + +void RemoteGraphicsLayer::noteSublayersChanged() +{ + noteLayerPropertiesChanged(RemoteLayerTreeTransaction::ChildrenChanged); + + // FIXME: Handle replica layers. +} + +void RemoteGraphicsLayer::recursiveCommitChanges() +{ + flushCompositingStateForThisLayerOnly(); + + for (size_t i = 0; i < children().size(); ++i) { + RemoteGraphicsLayer* graphicsLayer = static_cast<RemoteGraphicsLayer*>(children()[i]); + graphicsLayer->recursiveCommitChanges(); + } +} + } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeController.h b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeContext.h index 831d26f93..f5d7973fd 100644 --- a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeController.h +++ b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeContext.h @@ -23,25 +23,48 @@ * THE POSSIBILITY OF SUCH DAMAGE. */ -#ifndef RemoteLayerTree_h -#define RemoteLayerTree_h +#ifndef RemoteLayerTreeContext_h +#define RemoteLayerTreeContext_h #include <WebCore/GraphicsLayerFactory.h> +#include <WebCore/Timer.h> +#include <wtf/Vector.h> namespace WebKit { -class RemoteLayerTreeController : public WebCore::GraphicsLayerFactory { +class RemoteGraphicsLayer; +class RemoteLayerTreeTransaction; +class WebPage; + +class RemoteLayerTreeContext : public WebCore::GraphicsLayerFactory { public: - static PassOwnPtr<RemoteLayerTreeController> create(); - ~RemoteLayerTreeController(); + static PassOwnPtr<RemoteLayerTreeContext> create(WebPage*); + ~RemoteLayerTreeContext(); + + void setRootLayer(WebCore::GraphicsLayer*); + void layerWillBeDestroyed(RemoteGraphicsLayer*); + + void scheduleLayerFlush(); + + RemoteLayerTreeTransaction& currentTransaction(); private: - RemoteLayerTreeController(); + explicit RemoteLayerTreeContext(WebPage*); // WebCore::GraphicsLayerFactory virtual PassOwnPtr<WebCore::GraphicsLayer> createGraphicsLayer(WebCore::GraphicsLayerClient*) OVERRIDE; + + void layerFlushTimerFired(WebCore::Timer<RemoteLayerTreeContext>*); + void flushLayers(); + + WebPage* m_webPage; + WebCore::Timer<RemoteLayerTreeContext> m_layerFlushTimer; + + uint64_t m_rootLayerID; + Vector<uint64_t> m_destroyedLayers; + RemoteLayerTreeTransaction* m_currentTransaction; }; } // namespace WebKit -#endif // RemoteLayerTree_h +#endif // RemoteLayerTreeContext_h diff --git a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeContext.mm b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeContext.mm new file mode 100644 index 000000000..8503a1f4b --- /dev/null +++ b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeContext.mm @@ -0,0 +1,115 @@ +/* + * Copyright (C) 2012 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "config.h" +#import "RemoteLayerTreeContext.h" + +#import "RemoteGraphicsLayer.h" +#import "RemoteLayerTreeTransaction.h" +#import "RemoteLayerTreeHostMessages.h" +#import "WebPage.h" +#import <WebCore/Frame.h> +#import <WebCore/FrameView.h> +#import <WebCore/Page.h> +#import <wtf/PassOwnPtr.h> +#import <wtf/TemporaryChange.h> + +using namespace WebCore; + +namespace WebKit { + +PassOwnPtr<RemoteLayerTreeContext> RemoteLayerTreeContext::create(WebPage* webPage) +{ + return adoptPtr(new RemoteLayerTreeContext(webPage)); +} + +RemoteLayerTreeContext::RemoteLayerTreeContext(WebPage* webPage) + : m_webPage(webPage) + , m_layerFlushTimer(this, &RemoteLayerTreeContext::layerFlushTimerFired) + , m_rootLayerID(0) + , m_currentTransaction(nullptr) +{ +} + +RemoteLayerTreeContext::~RemoteLayerTreeContext() +{ +} + +void RemoteLayerTreeContext::setRootLayer(GraphicsLayer* rootLayer) +{ + ASSERT(rootLayer); + + m_rootLayerID = static_cast<RemoteGraphicsLayer*>(rootLayer)->layerID(); +} + +void RemoteLayerTreeContext::layerWillBeDestroyed(RemoteGraphicsLayer* graphicsLayer) +{ + ASSERT(!m_destroyedLayers.contains(graphicsLayer->layerID())); + + m_destroyedLayers.append(graphicsLayer->layerID()); +} + +void RemoteLayerTreeContext::scheduleLayerFlush() +{ + if (m_layerFlushTimer.isActive()) + return; + + m_layerFlushTimer.startOneShot(0); +} + +RemoteLayerTreeTransaction& RemoteLayerTreeContext::currentTransaction() +{ + ASSERT(m_currentTransaction); + + return *m_currentTransaction; +} + +PassOwnPtr<GraphicsLayer> RemoteLayerTreeContext::createGraphicsLayer(GraphicsLayerClient* client) +{ + return RemoteGraphicsLayer::create(client, this); +} + +void RemoteLayerTreeContext::layerFlushTimerFired(WebCore::Timer<RemoteLayerTreeContext>*) +{ + flushLayers(); +} + +void RemoteLayerTreeContext::flushLayers() +{ + ASSERT(!m_currentTransaction); + + RemoteLayerTreeTransaction transaction; + transaction.setRootLayerID(m_rootLayerID); + transaction.setDestroyedLayerIDs(std::move(m_destroyedLayers)); + + TemporaryChange<RemoteLayerTreeTransaction*> transactionChange(m_currentTransaction, &transaction); + + m_webPage->layoutIfNeeded(); + m_webPage->corePage()->mainFrame()->view()->flushCompositingStateIncludingSubframes(); + + m_webPage->send(Messages::RemoteLayerTreeHost::Commit(transaction)); +} + +} // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.h b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.h index d85c343fc..86f32b061 100644 --- a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.h +++ b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.h @@ -31,7 +31,7 @@ namespace WebKit { -class RemoteLayerTreeController; +class RemoteLayerTreeContext; class RemoteLayerTreeDrawingArea : public DrawingArea { public: @@ -49,7 +49,7 @@ private: virtual void setRootCompositingLayer(WebCore::GraphicsLayer*) OVERRIDE; virtual void scheduleCompositingLayerFlush() OVERRIDE; - OwnPtr<RemoteLayerTreeController> m_remoteLayerTreeController; + OwnPtr<RemoteLayerTreeContext> m_RemoteLayerTreeContext; }; } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.mm b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.mm index b6cfc574f..d014e16ad 100644 --- a/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.mm +++ b/Source/WebKit2/WebProcess/WebPage/mac/RemoteLayerTreeDrawingArea.mm @@ -26,7 +26,7 @@ #import "config.h" #import "RemoteLayerTreeDrawingArea.h" -#import "RemoteLayerTreeController.h" +#import "RemoteLayerTreeContext.h" using namespace WebCore; @@ -39,7 +39,7 @@ PassOwnPtr<RemoteLayerTreeDrawingArea> RemoteLayerTreeDrawingArea::create(WebPag RemoteLayerTreeDrawingArea::RemoteLayerTreeDrawingArea(WebPage* webPage, const WebPageCreationParameters&) : DrawingArea(DrawingAreaTypeRemoteLayerTree, webPage) - , m_remoteLayerTreeController(RemoteLayerTreeController::create()) + , m_RemoteLayerTreeContext(RemoteLayerTreeContext::create(webPage)) { } @@ -57,15 +57,17 @@ void RemoteLayerTreeDrawingArea::scroll(const IntRect& scrollRect, const IntSize GraphicsLayerFactory* RemoteLayerTreeDrawingArea::graphicsLayerFactory() { - return m_remoteLayerTreeController.get(); + return m_RemoteLayerTreeContext.get(); } -void RemoteLayerTreeDrawingArea::setRootCompositingLayer(GraphicsLayer*) +void RemoteLayerTreeDrawingArea::setRootCompositingLayer(GraphicsLayer* rootLayer) { + m_RemoteLayerTreeContext->setRootLayer(rootLayer); } void RemoteLayerTreeDrawingArea::scheduleCompositingLayerFlush() { + m_RemoteLayerTreeContext->scheduleLayerFlush(); } } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebPage/mac/WebPageMac.mm b/Source/WebKit2/WebProcess/WebPage/mac/WebPageMac.mm index 7b0c9ab36..5f09d751b 100644 --- a/Source/WebKit2/WebProcess/WebPage/mac/WebPageMac.mm +++ b/Source/WebKit2/WebProcess/WebPage/mac/WebPageMac.mm @@ -384,9 +384,9 @@ void WebPage::characterIndexForPoint(IntPoint point, uint64_t& index) return; HitTestResult result = frame->eventHandler()->hitTestResultAtPoint(point, false); - frame = result.innerNonSharedNode() ? result.innerNonSharedNode()->document()->frame() : m_page->focusController()->focusedOrMainFrame(); + frame = result.innerNonSharedNode() ? result.innerNodeFrame() : m_page->focusController()->focusedOrMainFrame(); - RefPtr<Range> range = frame->rangeForPoint(result.roundedPoint()); + RefPtr<Range> range = frame->rangeForPoint(result.roundedPointInInnerNodeFrame()); if (!range) return; @@ -679,7 +679,7 @@ bool WebPage::platformHasLocalDataForURL(const WebCore::KURL& url) NSMutableURLRequest* request = [[NSMutableURLRequest alloc] initWithURL:url]; [request setValue:(NSString*)userAgent() forHTTPHeaderField:@"User-Agent"]; NSCachedURLResponse *cachedResponse; - if (CFURLStorageSessionRef storageSession = ResourceHandle::currentStorageSession()) + if (CFURLStorageSessionRef storageSession = corePage()->mainFrame()->loader()->networkingContext()->storageSession()) cachedResponse = WKCachedResponseForRequest(storageSession, request); else cachedResponse = [[NSURLCache sharedURLCache] cachedResponseForRequest:request]; @@ -693,7 +693,7 @@ static NSCachedURLResponse *cachedResponseForURL(WebPage* webPage, const KURL& u RetainPtr<NSMutableURLRequest> request(AdoptNS, [[NSMutableURLRequest alloc] initWithURL:url]); [request.get() setValue:(NSString *)webPage->userAgent() forHTTPHeaderField:@"User-Agent"]; - if (CFURLStorageSessionRef storageSession = ResourceHandle::currentStorageSession()) + if (CFURLStorageSessionRef storageSession = webPage->corePage()->mainFrame()->loader()->networkingContext()->storageSession()) return WKCachedResponseForRequest(storageSession, request.get()); return [[NSURLCache sharedURLCache] cachedResponseForRequest:request.get()]; diff --git a/Source/WebKit2/WebProcess/WebPage/win/WebPageWin.cpp b/Source/WebKit2/WebProcess/WebPage/win/WebPageWin.cpp index 212fe6d4d..f9d733edd 100644 --- a/Source/WebKit2/WebProcess/WebPage/win/WebPageWin.cpp +++ b/Source/WebKit2/WebProcess/WebPage/win/WebPageWin.cpp @@ -266,15 +266,19 @@ static RetainPtr<CFCachedURLResponseRef> cachedResponseForURL(WebPage* webPage, { RetainPtr<CFURLRef> cfURL(AdoptCF, url.createCFURL()); RetainPtr<CFMutableURLRequestRef> request(AdoptCF, CFURLRequestCreateMutable(0, cfURL.get(), kCFURLRequestCachePolicyReloadIgnoringCache, 60, 0)); +#if NEEDS_FIXING_AFTER_R134960 wkSetRequestStorageSession(ResourceHandle::currentStorageSession(), request.get()); +#endif CFURLRequestSetHTTPHeaderFieldValue(request.get(), CFSTR("User-Agent"), webPage->userAgent().createCFString().get()); RetainPtr<CFURLCacheRef> cache; +#if NEEDS_FIXING_AFTER_R134960 if (CFURLStorageSessionRef currentStorageSession = ResourceHandle::currentStorageSession()) cache.adoptCF(wkCopyURLCache(currentStorageSession)); else cache.adoptCF(CFURLCacheCopySharedURLCache()); +#endif RetainPtr<CFCachedURLResponseRef> response(AdoptCF, CFURLCacheCopyResponseForRequest(cache.get(), request.get())); return response; diff --git a/Source/WebKit2/WebProcess/WebProcess.cpp b/Source/WebKit2/WebProcess/WebProcess.cpp index 60fe731b9..28b7bfd7b 100644 --- a/Source/WebKit2/WebProcess/WebProcess.cpp +++ b/Source/WebKit2/WebProcess/WebProcess.cpp @@ -37,6 +37,7 @@ #include "WebCoreArgumentCoders.h" #include "WebDatabaseManager.h" #include "WebFrame.h" +#include "WebFrameNetworkingContext.h" #include "WebGeolocationManagerMessages.h" #include "WebKeyValueStorageManager.h" #include "WebMediaCacheManager.h" @@ -98,6 +99,10 @@ #include "NetscapePluginModule.h" #endif +#if ENABLE(CUSTOM_PROTOCOLS) +#include "CustomProtocolManager.h" +#endif + using namespace JSC; using namespace WebCore; @@ -183,12 +188,15 @@ void WebProcess::initialize(CoreIPC::Connection::Identifier serverIdentifier, Ru { ASSERT(!m_connection); - m_connection = WebConnectionToUIProcess::create(this, serverIdentifier, runLoop); + m_connection = CoreIPC::Connection::createClientConnection(serverIdentifier, this, runLoop); + m_connection->setDidCloseOnConnectionWorkQueueCallback(ChildProcess::didCloseOnConnectionWorkQueue); + m_connection->setShouldExitOnSyncMessageSendFailure(true); + m_connection->addQueueClient(&m_eventDispatcher); + m_connection->addQueueClient(this); + m_connection->open(); - m_connection->connection()->addQueueClient(&m_eventDispatcher); - m_connection->connection()->addQueueClient(this); + m_webConnection = WebConnectionToUIProcess::create(this); - m_connection->connection()->open(); m_runLoop = runLoop; startRandomCrashThreadIfRequested(); @@ -274,9 +282,9 @@ void WebProcess::initializeWebProcess(const WebProcessCreationParameters& parame if (parameters.shouldUseFontSmoothing) setShouldUseFontSmoothing(true); -#if PLATFORM(MAC) || USE(CFNETWORK) +#if (PLATFORM(MAC) || USE(CFNETWORK)) && !PLATFORM(WIN) // FIXME (NetworkProcess): Send this identifier to network process. - WebCore::ResourceHandle::setPrivateBrowsingStorageSessionIdentifierBase(parameters.uiProcessBundleIdentifier); + WebFrameNetworkingContext::setPrivateBrowsingStorageSessionIdentifierBase(parameters.uiProcessBundleIdentifier); #endif #if ENABLE(NETWORK_PROCESS) @@ -655,6 +663,9 @@ void WebProcess::terminate() m_connection->invalidate(); m_connection = nullptr; + m_webConnection->invalidate(); + m_webConnection = nullptr; + platformTerminate(); m_runLoop->stop(); } @@ -707,6 +718,13 @@ void WebProcess::didReceiveMessage(CoreIPC::Connection* connection, CoreIPC::Mes return; } +#if ENABLE(CUSTOM_PROTOCOLS) + if (messageID.is<CoreIPC::MessageClassCustomProtocolManager>()) { + CustomProtocolManager::shared().didReceiveMessage(connection, messageID, decoder); + return; + } +#endif + if (messageID.is<CoreIPC::MessageClassWebPageGroupProxy>()) { uint64_t pageGroupID = decoder.destinationID(); if (!pageGroupID) @@ -1139,4 +1157,16 @@ void WebProcess::didGetPlugins(CoreIPC::Connection*, uint64_t requestID, const V } #endif // ENABLE(PLUGIN_PROCESS) +#if ENABLE(CUSTOM_PROTOCOLS) +void WebProcess::registerSchemeForCustomProtocol(const WTF::String& scheme) +{ + CustomProtocolManager::shared().registerScheme(scheme); +} + +void WebProcess::unregisterSchemeForCustomProtocol(const WTF::String& scheme) +{ + CustomProtocolManager::shared().unregisterScheme(scheme); +} +#endif + } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/WebProcess.h b/Source/WebKit2/WebProcess/WebProcess.h index 0b3c0fb99..eddccc153 100644 --- a/Source/WebKit2/WebProcess/WebProcess.h +++ b/Source/WebKit2/WebProcess/WebProcess.h @@ -115,15 +115,14 @@ public: void initialize(CoreIPC::Connection::Identifier, WebCore::RunLoop*); - CoreIPC::Connection* connection() const { return m_connection->connection(); } + CoreIPC::Connection* connection() const { return m_connection.get(); } WebCore::RunLoop* runLoop() const { return m_runLoop; } void addMessageReceiver(CoreIPC::StringReference messageReceiverName, CoreIPC::MessageReceiver*); void addMessageReceiver(CoreIPC::StringReference messageReceiverName, uint64_t destinationID, CoreIPC::MessageReceiver*); - void removeMessageReceiver(CoreIPC::StringReference messageReceiverName, uint64_t destinationID); - WebConnectionToUIProcess* webConnectionToUIProcess() const { return m_connection.get(); } + WebConnectionToUIProcess* webConnectionToUIProcess() const { return m_webConnection.get(); } WebPage* webPage(uint64_t pageID) const; void createWebPage(uint64_t pageID, const WebPageCreationParameters&); @@ -304,9 +303,16 @@ private: void didGetPlugins(CoreIPC::Connection*, uint64_t requestID, const Vector<WebCore::PluginInfo>&); #endif - RefPtr<WebConnectionToUIProcess> m_connection; +#if ENABLE(CUSTOM_PROTOCOLS) + void registerSchemeForCustomProtocol(const WTF::String&); + void unregisterSchemeForCustomProtocol(const WTF::String&); +#endif + + RefPtr<CoreIPC::Connection> m_connection; CoreIPC::MessageReceiverMap m_messageReceiverMap; + RefPtr<WebConnectionToUIProcess> m_webConnection; + HashMap<uint64_t, RefPtr<WebPage> > m_pageMap; HashMap<uint64_t, RefPtr<WebPageGroupProxy> > m_pageGroupMap; RefPtr<InjectedBundle> m_injectedBundle; diff --git a/Source/WebKit2/WebProcess/WebProcess.messages.in b/Source/WebKit2/WebProcess/WebProcess.messages.in index 2c1b43052..edcad34ff 100644 --- a/Source/WebKit2/WebProcess/WebProcess.messages.in +++ b/Source/WebKit2/WebProcess/WebProcess.messages.in @@ -101,4 +101,9 @@ messages -> WebProcess { #if PLATFORM(MAC) SetApplicationIsOccluded(bool flag); #endif + +#if ENABLE(CUSTOM_PROTOCOLS) + RegisterSchemeForCustomProtocol(WTF::String name) + UnregisterSchemeForCustomProtocol(WTF::String name) +#endif } diff --git a/Source/WebKit2/WebProcess/com.apple.WebProcess.sb.in b/Source/WebKit2/WebProcess/com.apple.WebProcess.sb.in index 84ff7ed21..7f386f911 100644 --- a/Source/WebKit2/WebProcess/com.apple.WebProcess.sb.in +++ b/Source/WebKit2/WebProcess/com.apple.WebProcess.sb.in @@ -117,6 +117,7 @@ (iokit-user-client-class "IOFramebufferSharedUserClient") (iokit-user-client-class "AppleGraphicsControlClient") (iokit-user-client-class "AppleSNBFBUserClient") + (iokit-user-client-class "AppleUpstreamUserClient") (iokit-user-client-class "AGPMClient") (iokit-user-client-class "IOHIDParamUserClient") (iokit-user-client-class "RootDomainUserClient") diff --git a/Source/WebKit2/WebProcess/mac/KeychainItemShimMethods.mm b/Source/WebKit2/WebProcess/mac/KeychainItemShimMethods.mm index 5759aa52f..2206f8b78 100644 --- a/Source/WebKit2/WebProcess/mac/KeychainItemShimMethods.mm +++ b/Source/WebKit2/WebProcess/mac/KeychainItemShimMethods.mm @@ -150,7 +150,7 @@ static BlockingResponseMap<SecKeychainItemResponseData>& responseMap() static uint64_t generateSecKeychainItemRequestID() { static int64_t uniqueSecKeychainItemRequestID; - return OSAtomicIncrement64Barrier(&uniqueSecKeychainItemRequestID); + return atomicIncrement(&uniqueSecKeychainItemRequestID); } void didReceiveSecKeychainItemResponse(uint64_t requestID, const SecKeychainItemResponseData& response) diff --git a/Source/WebKit2/WebProcess/mac/SecItemShimMethods.mm b/Source/WebKit2/WebProcess/mac/SecItemShimMethods.mm index 50cbb587a..6e6349dc7 100644 --- a/Source/WebKit2/WebProcess/mac/SecItemShimMethods.mm +++ b/Source/WebKit2/WebProcess/mac/SecItemShimMethods.mm @@ -48,7 +48,7 @@ static BlockingResponseMap<SecItemResponseData>& responseMap() static uint64_t generateSecItemRequestID() { static int64_t uniqueSecItemRequestID; - return OSAtomicIncrement64Barrier(&uniqueSecItemRequestID); + return atomicIncrement(&uniqueSecItemRequestID); } void didReceiveSecItemResponse(uint64_t requestID, const SecItemResponseData& response) diff --git a/Source/WebKit2/WebProcess/mac/WebProcessMac.mm b/Source/WebKit2/WebProcess/mac/WebProcessMac.mm index 001deb4c8..80d3e48a1 100644 --- a/Source/WebKit2/WebProcess/mac/WebProcessMac.mm +++ b/Source/WebKit2/WebProcess/mac/WebProcessMac.mm @@ -26,6 +26,7 @@ #import "config.h" #import "WebProcess.h" +#import "CustomProtocolManager.h" #import "SandboxExtension.h" #import "WKFullKeyboardAccessWatcher.h" #import "WebInspector.h" @@ -291,6 +292,11 @@ void WebProcess::platformInitializeWebProcess(const WebProcessCreationParameters // no window in WK2, NSApplication needs to use the focused page's focused element. Method methodToPatch = class_getInstanceMethod([NSApplication class], @selector(accessibilityFocusedUIElement)); method_setImplementation(methodToPatch, (IMP)NSApplicationAccessibilityFocusedUIElement); + + for (size_t i = 0; i < parameters.urlSchemesRegisteredForCustomProtocols.size(); ++i) + CustomProtocolManager::shared().registerScheme(parameters.urlSchemesRegisteredForCustomProtocols[i]); + + CustomProtocolManager::registerCustomProtocolClass(); } void WebProcess::initializeShim() diff --git a/Source/WebKit2/WebProcess/win/WebProcessWin.cpp b/Source/WebKit2/WebProcess/win/WebProcessWin.cpp index 40066a276..e731bcd8c 100644 --- a/Source/WebKit2/WebProcess/win/WebProcessWin.cpp +++ b/Source/WebKit2/WebProcess/win/WebProcessWin.cpp @@ -71,11 +71,13 @@ void WebProcess::platformSetCacheModel(CacheModel cacheModel) { #if USE(CFNETWORK) RetainPtr<CFStringRef> cfurlCacheDirectory; + +#if NEEDS_FIXING_AFTER_R134960 if (CFURLStorageSessionRef defaultStorageSession = ResourceHandle::defaultStorageSession()) cfurlCacheDirectory.adoptCF(wkCopyFoundationCacheDirectory(defaultStorageSession)); else cfurlCacheDirectory.adoptCF(wkCopyFoundationCacheDirectory(0)); - +#endif if (!cfurlCacheDirectory) cfurlCacheDirectory = WebCore::localUserSpecificStorageDirectory().createCFString(); @@ -101,11 +103,12 @@ void WebProcess::platformSetCacheModel(CacheModel cacheModel) pageCache()->setCapacity(pageCacheCapacity); RetainPtr<CFURLCacheRef> cfurlCache; +#if NEEDS_FIXING_AFTER_R134960 if (CFURLStorageSessionRef defaultStorageSession = ResourceHandle::defaultStorageSession()) cfurlCache.adoptCF(wkCopyURLCache(defaultStorageSession)); else cfurlCache.adoptCF(CFURLCacheCopySharedURLCache()); - +#endif CFURLCacheSetMemoryCapacity(cfurlCache.get(), urlCacheMemoryCapacity); CFURLCacheSetDiskCapacity(cfurlCache.get(), max<unsigned long>(urlCacheDiskCapacity, CFURLCacheDiskCapacity(cfurlCache.get()))); // Don't shrink a big disk cache, since that would cause churn. #endif @@ -118,11 +121,12 @@ void WebProcess::platformClearResourceCaches(ResourceCachesToClear cachesToClear return; RetainPtr<CFURLCacheRef> cache; +#if NEEDS_FIXING_AFTER_R134960 if (CFURLStorageSessionRef defaultStorageSession = ResourceHandle::defaultStorageSession()) cache.adoptCF(wkCopyURLCache(defaultStorageSession)); else cache.adoptCF(CFURLCacheCopySharedURLCache()); - +#endif CFURLCacheRemoveAllCachedResponses(cache.get()); #endif // USE(CFNETWORK) } @@ -133,7 +137,9 @@ void WebProcess::platformInitializeWebProcess(const WebProcessCreationParameters #if USE(CFNETWORK) RetainPtr<CFURLStorageSessionRef> defaultStorageSession(AdoptCF, wkDeserializeStorageSession(parameters.serializedDefaultStorageSession.get())); +#if NEEDS_FIXING_AFTER_R134960 ResourceHandle::setDefaultStorageSession(defaultStorageSession.get()); +#endif WebCookieManager::shared().setHTTPCookieAcceptPolicy(parameters.initialHTTPCookieAcceptPolicy); |
