Title: [256691] branches/safari-609-branch/Source
Revision
256691
Author
repst...@apple.com
Date
2020-02-14 19:02:39 -0800 (Fri, 14 Feb 2020)

Log Message

Cherry-pick r256482. rdar://problem/59478881

    Shrink CachedResource
    https://bugs.webkit.org/show_bug.cgi?id=207618

    Reviewed by Mark Lam.

    Source/WebCore:

    This patch shrinks sizeof(CachedResource) by 80 bytes by aggressively using bit-fields and Markable<>.
    For each enum class, we define `bitsOfXXX` value, which indicates # of bits to represent it. And using
    this value for bit-field's width.

    No behavior change.

    * loader/FetchOptions.h:
    (WebCore::FetchOptions::encode const):
    * loader/ResourceLoaderOptions.h:
    (WebCore::ResourceLoaderOptions::ResourceLoaderOptions):
    (WebCore::ResourceLoaderOptions::loadedFromOpaqueSource):
    * loader/cache/CachedImage.cpp:
    (WebCore::CachedImage::CachedImage):
    (WebCore::CachedImage::shouldDeferUpdateImageData const):
    (WebCore::CachedImage::didUpdateImageData):
    * loader/cache/CachedImage.h:
    * loader/cache/CachedResource.cpp:
    (WebCore::CachedResource::CachedResource):
    (WebCore::CachedResource::load):
    (WebCore::CachedResource::finish):
    * loader/cache/CachedResource.h:
    (WebCore::CachedResource::setStatus):
    * page/csp/ContentSecurityPolicyResponseHeaders.h:
    (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::isEmptyValue):
    (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::emptyValue):
    (WebCore::ContentSecurityPolicyResponseHeaders::ContentSecurityPolicyResponseHeaders):
    * platform/network/NetworkLoadMetrics.h:
    (WebCore::NetworkLoadMetrics::isolatedCopy const):
    (WebCore::NetworkLoadMetrics::clearNonTimingData):
    (WebCore::NetworkLoadMetrics::operator== const):
    (WebCore::NetworkLoadMetrics::encode const):
    (WebCore::NetworkLoadMetrics::decode):
    * platform/network/ResourceLoadPriority.h:
    * platform/network/ResourceRequestBase.h:
    (WebCore::ResourceRequestBase::ResourceRequestBase):
    * platform/network/ResourceResponseBase.h:
    * platform/network/StoredCredentialsPolicy.h:

    Source/WTF:

    * wtf/Markable.h:
    (WTF::Markable::asOptional const): Add helper method to get Optional easily from Markable.
    * wtf/ObjectIdentifier.h:
    (WTF::ObjectIdentifier::MarkableTraits::isEmptyValue):
    (WTF::ObjectIdentifier::MarkableTraits::emptyValue):
    (WTF::ObjectIdentifier::ObjectIdentifier): Add MarkableTraits for ObjectIdentifier.

    git-svn-id: https://svn.webkit.org/repository/webkit/trunk@256482 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Modified Paths

Diff

Modified: branches/safari-609-branch/Source/WTF/ChangeLog (256690 => 256691)


--- branches/safari-609-branch/Source/WTF/ChangeLog	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WTF/ChangeLog	2020-02-15 03:02:39 UTC (rev 256691)
@@ -1,5 +1,79 @@
 2020-02-14  Russell Epstein  <repst...@apple.com>
 
+        Cherry-pick r256482. rdar://problem/59478881
+
+    Shrink CachedResource
+    https://bugs.webkit.org/show_bug.cgi?id=207618
+    
+    Reviewed by Mark Lam.
+    
+    Source/WebCore:
+    
+    This patch shrinks sizeof(CachedResource) by 80 bytes by aggressively using bit-fields and Markable<>.
+    For each enum class, we define `bitsOfXXX` value, which indicates # of bits to represent it. And using
+    this value for bit-field's width.
+    
+    No behavior change.
+    
+    * loader/FetchOptions.h:
+    (WebCore::FetchOptions::encode const):
+    * loader/ResourceLoaderOptions.h:
+    (WebCore::ResourceLoaderOptions::ResourceLoaderOptions):
+    (WebCore::ResourceLoaderOptions::loadedFromOpaqueSource):
+    * loader/cache/CachedImage.cpp:
+    (WebCore::CachedImage::CachedImage):
+    (WebCore::CachedImage::shouldDeferUpdateImageData const):
+    (WebCore::CachedImage::didUpdateImageData):
+    * loader/cache/CachedImage.h:
+    * loader/cache/CachedResource.cpp:
+    (WebCore::CachedResource::CachedResource):
+    (WebCore::CachedResource::load):
+    (WebCore::CachedResource::finish):
+    * loader/cache/CachedResource.h:
+    (WebCore::CachedResource::setStatus):
+    * page/csp/ContentSecurityPolicyResponseHeaders.h:
+    (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::isEmptyValue):
+    (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::emptyValue):
+    (WebCore::ContentSecurityPolicyResponseHeaders::ContentSecurityPolicyResponseHeaders):
+    * platform/network/NetworkLoadMetrics.h:
+    (WebCore::NetworkLoadMetrics::isolatedCopy const):
+    (WebCore::NetworkLoadMetrics::clearNonTimingData):
+    (WebCore::NetworkLoadMetrics::operator== const):
+    (WebCore::NetworkLoadMetrics::encode const):
+    (WebCore::NetworkLoadMetrics::decode):
+    * platform/network/ResourceLoadPriority.h:
+    * platform/network/ResourceRequestBase.h:
+    (WebCore::ResourceRequestBase::ResourceRequestBase):
+    * platform/network/ResourceResponseBase.h:
+    * platform/network/StoredCredentialsPolicy.h:
+    
+    Source/WTF:
+    
+    * wtf/Markable.h:
+    (WTF::Markable::asOptional const): Add helper method to get Optional easily from Markable.
+    * wtf/ObjectIdentifier.h:
+    (WTF::ObjectIdentifier::MarkableTraits::isEmptyValue):
+    (WTF::ObjectIdentifier::MarkableTraits::emptyValue):
+    (WTF::ObjectIdentifier::ObjectIdentifier): Add MarkableTraits for ObjectIdentifier.
+    
+    git-svn-id: https://svn.webkit.org/repository/webkit/trunk@256482 268f45cc-cd09-0410-ab3c-d52691b4dbfc
+
+    2020-02-12  Yusuke Suzuki  <ysuz...@apple.com>
+
+            Shrink CachedResource
+            https://bugs.webkit.org/show_bug.cgi?id=207618
+
+            Reviewed by Mark Lam.
+
+            * wtf/Markable.h:
+            (WTF::Markable::asOptional const): Add helper method to get Optional easily from Markable.
+            * wtf/ObjectIdentifier.h:
+            (WTF::ObjectIdentifier::MarkableTraits::isEmptyValue):
+            (WTF::ObjectIdentifier::MarkableTraits::emptyValue):
+            (WTF::ObjectIdentifier::ObjectIdentifier): Add MarkableTraits for ObjectIdentifier.
+
+2020-02-14  Russell Epstein  <repst...@apple.com>
+
         Cherry-pick r254681. rdar://problem/59474790
 
     [Win] Fix AppleWin build

Modified: branches/safari-609-branch/Source/WTF/wtf/Markable.h (256690 => 256691)


--- branches/safari-609-branch/Source/WTF/wtf/Markable.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WTF/wtf/Markable.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -142,6 +142,11 @@
         return WTF::nullopt;
     }
 
+    Optional<T> asOptional() const
+    {
+        return Optional<T>(*this);
+    }
+
 private:
     T m_value;
 };

Modified: branches/safari-609-branch/Source/WTF/wtf/ObjectIdentifier.h (256690 => 256691)


--- branches/safari-609-branch/Source/WTF/wtf/ObjectIdentifier.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WTF/wtf/ObjectIdentifier.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -89,6 +89,18 @@
         return String::number(m_identifier);
     }
 
+    struct MarkableTraits {
+        static bool isEmptyValue(ObjectIdentifier identifier)
+        {
+            return !identifier.m_identifier;
+        }
+
+        static constexpr ObjectIdentifier emptyValue()
+        {
+            return ObjectIdentifier();
+        }
+    };
+
 private:
     template<typename U> friend ObjectIdentifier<U> makeObjectIdentifier(uint64_t);
     friend struct HashTraits<ObjectIdentifier>;
@@ -97,7 +109,7 @@
     static uint64_t hashTableDeletedValue() { return std::numeric_limits<uint64_t>::max(); }
     static bool isValidIdentifier(uint64_t identifier) { return identifier && identifier != hashTableDeletedValue(); }
 
-    explicit ObjectIdentifier(uint64_t identifier)
+    explicit constexpr ObjectIdentifier(uint64_t identifier)
         : m_identifier(identifier)
     {
     }

Modified: branches/safari-609-branch/Source/WebCore/ChangeLog (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/ChangeLog	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/ChangeLog	2020-02-15 03:02:39 UTC (rev 256691)
@@ -1,5 +1,110 @@
 2020-02-14  Russell Epstein  <repst...@apple.com>
 
+        Cherry-pick r256482. rdar://problem/59478881
+
+    Shrink CachedResource
+    https://bugs.webkit.org/show_bug.cgi?id=207618
+    
+    Reviewed by Mark Lam.
+    
+    Source/WebCore:
+    
+    This patch shrinks sizeof(CachedResource) by 80 bytes by aggressively using bit-fields and Markable<>.
+    For each enum class, we define `bitsOfXXX` value, which indicates # of bits to represent it. And using
+    this value for bit-field's width.
+    
+    No behavior change.
+    
+    * loader/FetchOptions.h:
+    (WebCore::FetchOptions::encode const):
+    * loader/ResourceLoaderOptions.h:
+    (WebCore::ResourceLoaderOptions::ResourceLoaderOptions):
+    (WebCore::ResourceLoaderOptions::loadedFromOpaqueSource):
+    * loader/cache/CachedImage.cpp:
+    (WebCore::CachedImage::CachedImage):
+    (WebCore::CachedImage::shouldDeferUpdateImageData const):
+    (WebCore::CachedImage::didUpdateImageData):
+    * loader/cache/CachedImage.h:
+    * loader/cache/CachedResource.cpp:
+    (WebCore::CachedResource::CachedResource):
+    (WebCore::CachedResource::load):
+    (WebCore::CachedResource::finish):
+    * loader/cache/CachedResource.h:
+    (WebCore::CachedResource::setStatus):
+    * page/csp/ContentSecurityPolicyResponseHeaders.h:
+    (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::isEmptyValue):
+    (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::emptyValue):
+    (WebCore::ContentSecurityPolicyResponseHeaders::ContentSecurityPolicyResponseHeaders):
+    * platform/network/NetworkLoadMetrics.h:
+    (WebCore::NetworkLoadMetrics::isolatedCopy const):
+    (WebCore::NetworkLoadMetrics::clearNonTimingData):
+    (WebCore::NetworkLoadMetrics::operator== const):
+    (WebCore::NetworkLoadMetrics::encode const):
+    (WebCore::NetworkLoadMetrics::decode):
+    * platform/network/ResourceLoadPriority.h:
+    * platform/network/ResourceRequestBase.h:
+    (WebCore::ResourceRequestBase::ResourceRequestBase):
+    * platform/network/ResourceResponseBase.h:
+    * platform/network/StoredCredentialsPolicy.h:
+    
+    Source/WTF:
+    
+    * wtf/Markable.h:
+    (WTF::Markable::asOptional const): Add helper method to get Optional easily from Markable.
+    * wtf/ObjectIdentifier.h:
+    (WTF::ObjectIdentifier::MarkableTraits::isEmptyValue):
+    (WTF::ObjectIdentifier::MarkableTraits::emptyValue):
+    (WTF::ObjectIdentifier::ObjectIdentifier): Add MarkableTraits for ObjectIdentifier.
+    
+    git-svn-id: https://svn.webkit.org/repository/webkit/trunk@256482 268f45cc-cd09-0410-ab3c-d52691b4dbfc
+
+    2020-02-12  Yusuke Suzuki  <ysuz...@apple.com>
+
+            Shrink CachedResource
+            https://bugs.webkit.org/show_bug.cgi?id=207618
+
+            Reviewed by Mark Lam.
+
+            This patch shrinks sizeof(CachedResource) by 80 bytes by aggressively using bit-fields and Markable<>.
+            For each enum class, we define `bitsOfXXX` value, which indicates # of bits to represent it. And using
+            this value for bit-field's width.
+
+            No behavior change.
+
+            * loader/FetchOptions.h:
+            (WebCore::FetchOptions::encode const):
+            * loader/ResourceLoaderOptions.h:
+            (WebCore::ResourceLoaderOptions::ResourceLoaderOptions):
+            (WebCore::ResourceLoaderOptions::loadedFromOpaqueSource):
+            * loader/cache/CachedImage.cpp:
+            (WebCore::CachedImage::CachedImage):
+            (WebCore::CachedImage::shouldDeferUpdateImageData const):
+            (WebCore::CachedImage::didUpdateImageData):
+            * loader/cache/CachedImage.h:
+            * loader/cache/CachedResource.cpp:
+            (WebCore::CachedResource::CachedResource):
+            (WebCore::CachedResource::load):
+            (WebCore::CachedResource::finish):
+            * loader/cache/CachedResource.h:
+            (WebCore::CachedResource::setStatus):
+            * page/csp/ContentSecurityPolicyResponseHeaders.h:
+            (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::isEmptyValue):
+            (WebCore::ContentSecurityPolicyResponseHeaders::MarkableTraits::emptyValue):
+            (WebCore::ContentSecurityPolicyResponseHeaders::ContentSecurityPolicyResponseHeaders):
+            * platform/network/NetworkLoadMetrics.h:
+            (WebCore::NetworkLoadMetrics::isolatedCopy const):
+            (WebCore::NetworkLoadMetrics::clearNonTimingData):
+            (WebCore::NetworkLoadMetrics::operator== const):
+            (WebCore::NetworkLoadMetrics::encode const):
+            (WebCore::NetworkLoadMetrics::decode):
+            * platform/network/ResourceLoadPriority.h:
+            * platform/network/ResourceRequestBase.h:
+            (WebCore::ResourceRequestBase::ResourceRequestBase):
+            * platform/network/ResourceResponseBase.h:
+            * platform/network/StoredCredentialsPolicy.h:
+
+2020-02-14  Russell Epstein  <repst...@apple.com>
+
         Cherry-pick r256423. rdar://problem/59478731
 
     Compress ImmutableStyleProperties by using PackedPtr

Modified: branches/safari-609-branch/Source/WebCore/loader/FetchOptions.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/loader/FetchOptions.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/loader/FetchOptions.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -30,6 +30,7 @@
 
 #include "DocumentIdentifier.h"
 #include "ReferrerPolicy.h"
+#include <wtf/Markable.h>
 #include <wtf/text/WTFString.h>
 
 namespace WebCore {
@@ -58,7 +59,7 @@
     ReferrerPolicy referrerPolicy { ReferrerPolicy::EmptyString };
     bool keepAlive { false };
     String integrity;
-    Optional<DocumentIdentifier> clientIdentifier;
+    Markable<DocumentIdentifier, DocumentIdentifier::MarkableTraits> clientIdentifier;
 };
 
 inline FetchOptions::FetchOptions(Destination destination, Mode mode, Credentials credentials, Cache cache, Redirect redirect, ReferrerPolicy referrerPolicy, String&& integrity, bool keepAlive)
@@ -228,7 +229,7 @@
 template<class Encoder> inline void FetchOptions::encode(Encoder& encoder) const
 {
     encodePersistent(encoder);
-    encoder << clientIdentifier;
+    encoder << clientIdentifier.asOptional();
 }
 
 template<class Decoder> inline Optional<FetchOptions> FetchOptions::decode(Decoder& decoder)

Modified: branches/safari-609-branch/Source/WebCore/loader/ResourceLoaderOptions.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/loader/ResourceLoaderOptions.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/loader/ResourceLoaderOptions.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -46,6 +46,7 @@
     SendCallbacks,
     DoNotSendCallbacks
 };
+static constexpr unsigned bitWidthOfSendCallbackPolicy = 1;
 
 // FIXME: These options are named poorly. We only implement force disabling content sniffing, not enabling it,
 // and even that only on some platforms.
@@ -53,51 +54,61 @@
     SniffContent,
     DoNotSniffContent
 };
+static constexpr unsigned bitWidthOfContentSniffingPolicy = 1;
 
 enum class DataBufferingPolicy : uint8_t {
     BufferData,
     DoNotBufferData
 };
+static constexpr unsigned bitWidthOfDataBufferingPolicy = 1;
 
 enum class SecurityCheckPolicy : uint8_t {
     SkipSecurityCheck,
     DoSecurityCheck
 };
+static constexpr unsigned bitWidthOfSecurityCheckPolicy = 1;
 
 enum class CertificateInfoPolicy : uint8_t {
     IncludeCertificateInfo,
     DoNotIncludeCertificateInfo
 };
+static constexpr unsigned bitWidthOfCertificateInfoPolicy = 1;
 
 enum class ContentSecurityPolicyImposition : uint8_t {
     SkipPolicyCheck,
     DoPolicyCheck
 };
+static constexpr unsigned bitWidthOfContentSecurityPolicyImposition = 1;
 
 enum class DefersLoadingPolicy : uint8_t {
     AllowDefersLoading,
     DisallowDefersLoading
 };
+static constexpr unsigned bitWidthOfDefersLoadingPolicy = 1;
 
 enum class CachingPolicy : uint8_t {
     AllowCaching,
     DisallowCaching
 };
+static constexpr unsigned bitWidthOfCachingPolicy = 1;
 
 enum class ClientCredentialPolicy : uint8_t {
     CannotAskClientForCredentials,
     MayAskClientForCredentials
 };
+static constexpr unsigned bitWidthOfClientCredentialPolicy = 1;
 
 enum class SameOriginDataURLFlag : uint8_t {
     Set,
     Unset
 };
+static constexpr unsigned bitWidthOfSameOriginDataURLFlag = 1;
 
 enum class InitiatorContext : uint8_t {
     Document,
     Worker,
 };
+static constexpr unsigned bitWidthOfInitiatorContext = 1;
 
 enum class ServiceWorkersMode : uint8_t {
     All,
@@ -104,11 +115,13 @@
     None,
     Only // An error will happen if service worker is not handling the fetch. Used to bypass preflight safely.
 };
+static constexpr unsigned bitWidthOfServiceWorkersMode = 2;
 
 enum class ApplicationCacheMode : uint8_t {
     Use,
     Bypass
 };
+static constexpr unsigned bitWidthOfApplicationCacheMode = 1;
 
 // FIXME: These options are named poorly. We only implement force disabling content encoding sniffing, not enabling it,
 // and even that only on some platforms.
@@ -116,6 +129,7 @@
     Sniff,
     DoNotSniff,
 };
+static constexpr unsigned bitWidthOfContentEncodingSniffingPolicy = 1;
 
 enum class PreflightPolicy : uint8_t {
     Consider,
@@ -122,20 +136,45 @@
     Force,
     Prevent
 };
+static constexpr unsigned bitWidthOfPreflightPolicy = 2;
 
 enum class LoadedFromOpaqueSource : uint8_t {
     Yes,
     No
 };
+static constexpr unsigned bitWidthOfLoadedFromOpaqueSource = 1;
 
 struct ResourceLoaderOptions : public FetchOptions {
-    ResourceLoaderOptions() { }
+    ResourceLoaderOptions()
+        : ResourceLoaderOptions(FetchOptions())
+    {
+    }
 
-    ResourceLoaderOptions(FetchOptions options) : FetchOptions { WTFMove(options) } { }
+    ResourceLoaderOptions(FetchOptions options)
+        : FetchOptions { WTFMove(options) }
+        , sendLoadCallbacks(SendCallbackPolicy::DoNotSendCallbacks)
+        , sniffContent(ContentSniffingPolicy::DoNotSniffContent)
+        , sniffContentEncoding(ContentEncodingSniffingPolicy::Sniff)
+        , dataBufferingPolicy(DataBufferingPolicy::BufferData)
+        , storedCredentialsPolicy(StoredCredentialsPolicy::DoNotUse)
+        , securityCheck(SecurityCheckPolicy::DoSecurityCheck)
+        , certificateInfoPolicy(CertificateInfoPolicy::DoNotIncludeCertificateInfo)
+        , contentSecurityPolicyImposition(ContentSecurityPolicyImposition::DoPolicyCheck)
+        , defersLoadingPolicy(DefersLoadingPolicy::AllowDefersLoading)
+        , cachingPolicy(CachingPolicy::AllowCaching)
+        , sameOriginDataURLFlag(SameOriginDataURLFlag::Unset)
+        , initiatorContext(InitiatorContext::Document)
+        , serviceWorkersMode(ServiceWorkersMode::All)
+        , applicationCacheMode(ApplicationCacheMode::Use)
+        , clientCredentialPolicy(ClientCredentialPolicy::CannotAskClientForCredentials)
+        , preflightPolicy(PreflightPolicy::Consider)
+        , loadedFromOpaqueSource(LoadedFromOpaqueSource::No)
+    { }
 
     ResourceLoaderOptions(SendCallbackPolicy sendLoadCallbacks, ContentSniffingPolicy sniffContent, DataBufferingPolicy dataBufferingPolicy, StoredCredentialsPolicy storedCredentialsPolicy, ClientCredentialPolicy credentialPolicy, FetchOptions::Credentials credentials, SecurityCheckPolicy securityCheck, FetchOptions::Mode mode, CertificateInfoPolicy certificateInfoPolicy, ContentSecurityPolicyImposition contentSecurityPolicyImposition, DefersLoadingPolicy defersLoadingPolicy, CachingPolicy cachingPolicy)
         : sendLoadCallbacks(sendLoadCallbacks)
         , sniffContent(sniffContent)
+        , sniffContentEncoding(ContentEncodingSniffingPolicy::Sniff)
         , dataBufferingPolicy(dataBufferingPolicy)
         , storedCredentialsPolicy(storedCredentialsPolicy)
         , securityCheck(securityCheck)
@@ -143,7 +182,14 @@
         , contentSecurityPolicyImposition(contentSecurityPolicyImposition)
         , defersLoadingPolicy(defersLoadingPolicy)
         , cachingPolicy(cachingPolicy)
+        , sameOriginDataURLFlag(SameOriginDataURLFlag::Unset)
+        , initiatorContext(InitiatorContext::Document)
+        , serviceWorkersMode(ServiceWorkersMode::All)
+        , applicationCacheMode(ApplicationCacheMode::Use)
         , clientCredentialPolicy(credentialPolicy)
+        , preflightPolicy(PreflightPolicy::Consider)
+        , loadedFromOpaqueSource(LoadedFromOpaqueSource::No)
+
     {
         this->credentials = credentials;
         this->mode = mode;
@@ -150,29 +196,29 @@
     }
 
 #if ENABLE(SERVICE_WORKER)
-    Optional<ServiceWorkerRegistrationIdentifier> serviceWorkerRegistrationIdentifier;
+    Markable<ServiceWorkerRegistrationIdentifier, ServiceWorkerRegistrationIdentifier::MarkableTraits> serviceWorkerRegistrationIdentifier;
 #endif
+    Markable<ContentSecurityPolicyResponseHeaders, ContentSecurityPolicyResponseHeaders::MarkableTraits> cspResponseHeaders;
     OptionSet<HTTPHeadersToKeepFromCleaning> httpHeadersToKeep;
-    Optional<ContentSecurityPolicyResponseHeaders> cspResponseHeaders;
-    unsigned maxRedirectCount { 20 };
+    uint8_t maxRedirectCount { 20 };
 
-    SendCallbackPolicy sendLoadCallbacks { SendCallbackPolicy::DoNotSendCallbacks };
-    ContentSniffingPolicy sniffContent { ContentSniffingPolicy::DoNotSniffContent };
-    ContentEncodingSniffingPolicy sniffContentEncoding { ContentEncodingSniffingPolicy::Sniff };
-    DataBufferingPolicy dataBufferingPolicy { DataBufferingPolicy::BufferData };
-    StoredCredentialsPolicy storedCredentialsPolicy { StoredCredentialsPolicy::DoNotUse };
-    SecurityCheckPolicy securityCheck { SecurityCheckPolicy::DoSecurityCheck };
-    CertificateInfoPolicy certificateInfoPolicy { CertificateInfoPolicy::DoNotIncludeCertificateInfo };
-    ContentSecurityPolicyImposition contentSecurityPolicyImposition { ContentSecurityPolicyImposition::DoPolicyCheck };
-    DefersLoadingPolicy defersLoadingPolicy { DefersLoadingPolicy::AllowDefersLoading };
-    CachingPolicy cachingPolicy { CachingPolicy::AllowCaching };
-    SameOriginDataURLFlag sameOriginDataURLFlag { SameOriginDataURLFlag::Unset };
-    InitiatorContext initiatorContext { InitiatorContext::Document };
-    ServiceWorkersMode serviceWorkersMode { ServiceWorkersMode::All };
-    ApplicationCacheMode applicationCacheMode { ApplicationCacheMode::Use };
-    ClientCredentialPolicy clientCredentialPolicy { ClientCredentialPolicy::CannotAskClientForCredentials };
-    PreflightPolicy preflightPolicy { PreflightPolicy::Consider };
-    LoadedFromOpaqueSource loadedFromOpaqueSource { LoadedFromOpaqueSource::No };
+    SendCallbackPolicy sendLoadCallbacks : bitWidthOfSendCallbackPolicy;
+    ContentSniffingPolicy sniffContent : bitWidthOfContentSniffingPolicy;
+    ContentEncodingSniffingPolicy sniffContentEncoding : bitWidthOfContentEncodingSniffingPolicy;
+    DataBufferingPolicy dataBufferingPolicy : bitWidthOfDataBufferingPolicy;
+    StoredCredentialsPolicy storedCredentialsPolicy : bitWidthOfStoredCredentialsPolicy;
+    SecurityCheckPolicy securityCheck : bitWidthOfSecurityCheckPolicy;
+    CertificateInfoPolicy certificateInfoPolicy : bitWidthOfCertificateInfoPolicy;
+    ContentSecurityPolicyImposition contentSecurityPolicyImposition : bitWidthOfContentSecurityPolicyImposition;
+    DefersLoadingPolicy defersLoadingPolicy : bitWidthOfDefersLoadingPolicy;
+    CachingPolicy cachingPolicy : bitWidthOfCachingPolicy;
+    SameOriginDataURLFlag sameOriginDataURLFlag : bitWidthOfSameOriginDataURLFlag;
+    InitiatorContext initiatorContext : bitWidthOfInitiatorContext;
+    ServiceWorkersMode serviceWorkersMode : bitWidthOfServiceWorkersMode;
+    ApplicationCacheMode applicationCacheMode : bitWidthOfApplicationCacheMode;
+    ClientCredentialPolicy clientCredentialPolicy : bitWidthOfClientCredentialPolicy;
+    PreflightPolicy preflightPolicy : bitWidthOfPreflightPolicy;
+    LoadedFromOpaqueSource loadedFromOpaqueSource : bitWidthOfLoadedFromOpaqueSource;
 };
 
 } // namespace WebCore

Modified: branches/safari-609-branch/Source/WebCore/loader/cache/CachedImage.cpp (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/loader/cache/CachedImage.cpp	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/loader/cache/CachedImage.cpp	2020-02-15 03:02:39 UTC (rev 256691)
@@ -57,6 +57,10 @@
 
 CachedImage::CachedImage(CachedResourceRequest&& request, const PAL::SessionID& sessionID, const CookieJar* cookieJar)
     : CachedResource(WTFMove(request), Type::ImageResource, sessionID, cookieJar)
+    , m_updateImageDataCount(0)
+    , m_isManuallyCached(false)
+    , m_shouldPaintBrokenImage(true)
+    , m_forceUpdateImageDataEnabledForTesting(false)
 {
     setStatus(Unknown);
 }
@@ -64,6 +68,10 @@
 CachedImage::CachedImage(Image* image, const PAL::SessionID& sessionID, const CookieJar* cookieJar)
     : CachedResource(URL(), Type::ImageResource, sessionID, cookieJar)
     , m_image(image)
+    , m_updateImageDataCount(0)
+    , m_isManuallyCached(false)
+    , m_shouldPaintBrokenImage(true)
+    , m_forceUpdateImageDataEnabledForTesting(false)
 {
 }
 
@@ -70,7 +78,10 @@
 CachedImage::CachedImage(const URL& url, Image* image, const PAL::SessionID& sessionID, const CookieJar* cookieJar, const String& domainForCachePartition)
     : CachedResource(url, Type::ImageResource, sessionID, cookieJar)
     , m_image(image)
+    , m_updateImageDataCount(0)
     , m_isManuallyCached(true)
+    , m_shouldPaintBrokenImage(true)
+    , m_forceUpdateImageDataEnabledForTesting(false)
 {
     m_resourceRequest.setDomainForCachePartition(domainForCachePartition);
 
@@ -493,7 +504,7 @@
 bool CachedImage::shouldDeferUpdateImageData() const
 {
     static const double updateImageDataBackoffIntervals[] = { 0, 1, 3, 6, 15 };
-    unsigned interval = std::min<unsigned>(m_updateImageDataCount, 4);
+    unsigned interval = m_updateImageDataCount;
 
     // The first time through, the chunk time will be 0 and the image will get an update.
     return (MonotonicTime::now() - m_lastUpdateImageDataTime).seconds() < updateImageDataBackoffIntervals[interval];
@@ -515,8 +526,9 @@
 void CachedImage::didUpdateImageData()
 {
     m_lastUpdateImageDataTime = MonotonicTime::now();
-    ASSERT(m_updateImageDataCount < std::numeric_limits<unsigned>::max());
-    ++m_updateImageDataCount;
+    unsigned previous = m_updateImageDataCount;
+    if (previous != maxUpdateImageDataCount)
+        m_updateImageDataCount += 1;
 }
 
 EncodedDataStatus CachedImage::updateImageData(bool allDataReceived)

Modified: branches/safari-609-branch/Source/WebCore/loader/cache/CachedImage.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/loader/cache/CachedImage.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/loader/cache/CachedImage.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -184,10 +184,11 @@
 
     MonotonicTime m_lastUpdateImageDataTime;
 
-    unsigned m_updateImageDataCount { 0 };
-    bool m_isManuallyCached { false };
-    bool m_shouldPaintBrokenImage { true };
-    bool m_forceUpdateImageDataEnabledForTesting { false };
+    static constexpr unsigned maxUpdateImageDataCount = 4;
+    unsigned m_updateImageDataCount : 3;
+    bool m_isManuallyCached : 1;
+    bool m_shouldPaintBrokenImage : 1;
+    bool m_forceUpdateImageDataEnabledForTesting : 1;
 };
 
 } // namespace WebCore

Modified: branches/safari-609-branch/Source/WebCore/loader/cache/CachedResource.cpp (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/loader/cache/CachedResource.cpp	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/loader/cache/CachedResource.cpp	2020-02-15 03:02:39 UTC (rev 256691)
@@ -129,10 +129,17 @@
     , m_fragmentIdentifierForRequest(request.releaseFragmentIdentifier())
     , m_origin(request.releaseOrigin())
     , m_initiatorName(request.initiatorName())
+    , m_type(type)
+    , m_preloadResult(PreloadResult::PreloadNotReferenced)
+    , m_responseTainting(ResourceResponse::Tainting::Basic)
     , m_loadPriority(defaultPriorityForResourceType(type))
-    , m_type(type)
+    , m_status(Pending)
+    , m_requestedFromNetworkingLayer(false)
+    , m_inCache(false)
+    , m_loading(false)
     , m_isLinkPreload(request.isLinkPreload())
     , m_hasUnknownEncoding(request.isLinkPreload())
+    , m_switchingClientsToRevalidatedResource(false)
     , m_ignoreForRequestCount(request.ignoreForRequestCount())
 {
     ASSERT(m_sessionID.isValid());
@@ -157,8 +164,17 @@
     , m_cookieJar(cookieJar)
     , m_responseTimestamp(WallTime::now())
     , m_fragmentIdentifierForRequest(CachedResourceRequest::splitFragmentIdentifierFromRequestURL(m_resourceRequest))
+    , m_type(type)
+    , m_preloadResult(PreloadResult::PreloadNotReferenced)
+    , m_responseTainting(ResourceResponse::Tainting::Basic)
     , m_status(Cached)
-    , m_type(type)
+    , m_requestedFromNetworkingLayer(false)
+    , m_inCache(false)
+    , m_loading(false)
+    , m_isLinkPreload(false)
+    , m_hasUnknownEncoding(false)
+    , m_switchingClientsToRevalidatedResource(false)
+    , m_ignoreForRequestCount(false)
 {
     ASSERT(m_sessionID.isValid());
 #ifndef NDEBUG
@@ -312,7 +328,7 @@
             failBeforeStarting();
             return;
         }
-        m_status = Pending;
+        setStatus(Pending);
     });
 }
 
@@ -399,7 +415,7 @@
 void CachedResource::finish()
 {
     if (!errorOccurred())
-        m_status = Cached;
+        setStatus(Cached);
 }
 
 void CachedResource::setCrossOrigin()

Modified: branches/safari-609-branch/Source/WebCore/loader/cache/CachedResource.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/loader/cache/CachedResource.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/loader/cache/CachedResource.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -77,20 +77,23 @@
         Icon,
         Beacon,
         Ping,
-        SVGDocumentResource
 #if ENABLE(XSLT)
-        , XSLStyleSheet
+        XSLStyleSheet,
 #endif
-        , LinkPrefetch
+        LinkPrefetch,
 #if ENABLE(VIDEO_TRACK)
-        , TextTrackResource
+        TextTrackResource,
 #endif
 #if ENABLE(APPLICATION_MANIFEST)
-        , ApplicationManifest
+        ApplicationManifest,
 #endif
+        SVGDocumentResource,
+        LastType = SVGDocumentResource,
     };
+    static constexpr unsigned bitWidthOfType = 5;
+    static_assert(static_cast<unsigned>(Type::LastType) <= ((1U << bitWidthOfType) - 1));
 
-    enum Status {
+    enum Status : uint8_t {
         Unknown,      // let cache decide what to do with it
         Pending,      // only partially loaded
         Cached,       // regular case
@@ -97,6 +100,8 @@
         LoadError,
         DecodeError
     };
+    static constexpr unsigned bitWidthOfStatus = 3;
+    static_assert(static_cast<unsigned>(DecodeError) <= ((1ULL << bitWidthOfStatus) - 1));
 
     CachedResource(CachedResourceRequest&&, Type, const PAL::SessionID&, const CookieJar*);
     virtual ~CachedResource();
@@ -142,6 +147,8 @@
         PreloadReferencedWhileLoading,
         PreloadReferencedWhileComplete
     };
+    static constexpr unsigned bitWidthOfPreloadResult = 2;
+
     PreloadResult preloadResult() const { return static_cast<PreloadResult>(m_preloadResult); }
 
     virtual void didAddClient(CachedResourceClient&);
@@ -152,7 +159,11 @@
     unsigned numberOfClients() const { return m_clients.size(); }
 
     Status status() const { return static_cast<Status>(m_status); }
-    void setStatus(Status status) { m_status = status; }
+    void setStatus(Status status)
+    {
+        m_status = status;
+        ASSERT(this->status() == status);
+    }
 
     unsigned size() const { return encodedSize() + decodedSize() + overheadSize(); }
     unsigned encodedSize() const { return m_encodedSize; }
@@ -353,8 +364,6 @@
     RefPtr<SecurityOrigin> m_origin;
     AtomString m_initiatorName;
 
-    RedirectChainCacheStatus m_redirectChainCacheStatus;
-
     unsigned m_encodedSize { 0 };
     unsigned m_decodedSize { 0 };
     unsigned m_accessCount { 0 };
@@ -361,23 +370,23 @@
     unsigned m_handleCount { 0 };
     unsigned m_preloadCount { 0 };
 
-    unsigned m_status { Pending }; // Status
+    RedirectChainCacheStatus m_redirectChainCacheStatus;
 
-    PreloadResult m_preloadResult { PreloadResult::PreloadNotReferenced };
+    Type m_type : bitWidthOfType;
 
-    ResourceResponse::Tainting m_responseTainting { ResourceResponse::Tainting::Basic };
-    ResourceLoadPriority m_loadPriority;
+    PreloadResult m_preloadResult : bitWidthOfPreloadResult;
+    ResourceResponse::Tainting m_responseTainting : ResourceResponse::bitWidthOfTainting;
+    ResourceLoadPriority m_loadPriority : bitWidthOfResourceLoadPriority;
 
-    Type m_type; // Type
+    Status m_status : bitWidthOfStatus;
+    bool m_requestedFromNetworkingLayer : 1;
+    bool m_inCache : 1;
+    bool m_loading : 1;
+    bool m_isLinkPreload : 1;
+    bool m_hasUnknownEncoding : 1;
+    bool m_switchingClientsToRevalidatedResource : 1;
+    bool m_ignoreForRequestCount : 1;
 
-    bool m_requestedFromNetworkingLayer { false };
-    bool m_inCache { false };
-    bool m_loading { false };
-    bool m_isLinkPreload { false };
-    bool m_hasUnknownEncoding { false };
-    bool m_switchingClientsToRevalidatedResource { false };
-    bool m_ignoreForRequestCount { false };
-
 #ifndef NDEBUG
     bool m_deleted { false };
     unsigned m_lruIndex { 0 };

Modified: branches/safari-609-branch/Source/WebCore/page/csp/ContentSecurityPolicyResponseHeaders.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/page/csp/ContentSecurityPolicyResponseHeaders.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/page/csp/ContentSecurityPolicyResponseHeaders.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -50,11 +50,28 @@
     template <class Encoder> void encode(Encoder&) const;
     template <class Decoder> static bool decode(Decoder&, ContentSecurityPolicyResponseHeaders&);
 
+    enum EmptyTag { Empty };
+    struct MarkableTraits {
+        static bool isEmptyValue(const ContentSecurityPolicyResponseHeaders& identifier)
+        {
+            return identifier.m_emptyForMarkable;
+        }
+
+        static ContentSecurityPolicyResponseHeaders emptyValue()
+        {
+            return ContentSecurityPolicyResponseHeaders(Empty);
+        }
+    };
+
 private:
     friend class ContentSecurityPolicy;
+    ContentSecurityPolicyResponseHeaders(EmptyTag)
+        : m_emptyForMarkable(true)
+    { }
 
     Vector<std::pair<String, ContentSecurityPolicyHeaderType>> m_headers;
     int m_httpStatusCode { 0 };
+    bool m_emptyForMarkable { false };
 };
 
 template <class Encoder>

Modified: branches/safari-609-branch/Source/WebCore/platform/network/NetworkLoadMetrics.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/platform/network/NetworkLoadMetrics.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/platform/network/NetworkLoadMetrics.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -70,9 +70,9 @@
 
         copy.remoteAddress = remoteAddress.isolatedCopy();
         copy.connectionIdentifier = connectionIdentifier.isolatedCopy();
-        copy.priority = priority;
         copy.tlsProtocol = tlsProtocol.isolatedCopy();
         copy.tlsCipher = tlsCipher.isolatedCopy();
+        copy.priority = priority;
         copy.requestHeaders = requestHeaders.isolatedCopy();
 
         copy.requestHeaderBytesSent = requestHeaderBytesSent;
@@ -103,9 +103,9 @@
     {
         remoteAddress = String();
         connectionIdentifier = String();
-        priority = NetworkLoadPriority::Unknown;
         tlsProtocol = String();
         tlsCipher = String();
+        priority = NetworkLoadPriority::Unknown;
         requestHeaders.clear();
         requestHeaderBytesSent = std::numeric_limits<uint32_t>::max();
         requestBodyBytesSent = std::numeric_limits<uint64_t>::max();
@@ -128,9 +128,9 @@
             && protocol == other.protocol
             && remoteAddress == other.remoteAddress
             && connectionIdentifier == other.connectionIdentifier
-            && priority == other.priority
             && tlsProtocol == other.tlsProtocol
             && tlsCipher == other.tlsCipher
+            && priority == other.priority
             && requestHeaders == other.requestHeaders
             && requestHeaderBytesSent == other.requestHeaderBytesSent
             && requestBodyBytesSent == other.requestBodyBytesSent
@@ -166,12 +166,12 @@
 
     String remoteAddress;
     String connectionIdentifier;
-    NetworkLoadPriority priority;
 
     String tlsProtocol;
     String tlsCipher;
 
     // Whether or not all of the properties (0 or otherwise) have been set.
+    NetworkLoadPriority priority;
     bool complete { false };
 
     HTTPHeaderMap requestHeaders;
@@ -202,9 +202,9 @@
     encoder << protocol;
     encoder << remoteAddress;
     encoder << connectionIdentifier;
-    encoder << priority;
     encoder << tlsProtocol;
     encoder << tlsCipher;
+    encoder << priority;
     encoder << requestHeaders;
     encoder << requestHeaderBytesSent;
     encoder << requestBodyBytesSent;
@@ -228,9 +228,9 @@
         && decoder.decode(metrics.protocol)
         && decoder.decode(metrics.remoteAddress)
         && decoder.decode(metrics.connectionIdentifier)
-        && decoder.decode(metrics.priority)
         && decoder.decode(metrics.tlsProtocol)
         && decoder.decode(metrics.tlsCipher)
+        && decoder.decode(metrics.priority)
         && decoder.decode(metrics.requestHeaders)
         && decoder.decode(metrics.requestHeaderBytesSent)
         && decoder.decode(metrics.requestBodyBytesSent)

Modified: branches/safari-609-branch/Source/WebCore/platform/network/ResourceLoadPriority.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/platform/network/ResourceLoadPriority.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/platform/network/ResourceLoadPriority.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -37,6 +37,8 @@
     Lowest = VeryLow,
     Highest = VeryHigh,
 };
+static constexpr unsigned bitWidthOfResourceLoadPriority = 3;
+static_assert(static_cast<unsigned>(ResourceLoadPriority::Highest) <= ((1U << bitWidthOfResourceLoadPriority) - 1));
 
 static const unsigned resourceLoadPriorityCount { static_cast<unsigned>(ResourceLoadPriority::Highest) + 1 };
 

Modified: branches/safari-609-branch/Source/WebCore/platform/network/ResourceRequestBase.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/platform/network/ResourceRequestBase.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/platform/network/ResourceRequestBase.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -201,8 +201,13 @@
 protected:
     // Used when ResourceRequest is initialized from a platform representation of the request
     ResourceRequestBase()
-        : m_platformRequestUpdated(true)
+        : m_allowCookies(false)
+        , m_resourceRequestUpdated(false)
+        , m_platformRequestUpdated(true)
+        , m_resourceRequestBodyUpdated(false)
         , m_platformRequestBodyUpdated(true)
+        , m_hiddenFromInspector(false)
+        , m_isTopSite(false)
     {
     }
 
@@ -213,7 +218,11 @@
         , m_cachePolicy(policy)
         , m_allowCookies(true)
         , m_resourceRequestUpdated(true)
+        , m_platformRequestUpdated(false)
         , m_resourceRequestBodyUpdated(true)
+        , m_platformRequestBodyUpdated(false)
+        , m_hiddenFromInspector(false)
+        , m_isTopSite(false)
     {
     }
 
@@ -240,13 +249,13 @@
     ResourceLoadPriority m_priority { ResourceLoadPriority::Low };
     Requester m_requester { Requester::Unspecified };
     Optional<int> m_inspectorInitiatorNodeIdentifier;
-    bool m_allowCookies { false };
-    mutable bool m_resourceRequestUpdated { false };
-    mutable bool m_platformRequestUpdated { false };
-    mutable bool m_resourceRequestBodyUpdated { false };
-    mutable bool m_platformRequestBodyUpdated { false };
-    bool m_hiddenFromInspector { false };
-    bool m_isTopSite { false };
+    bool m_allowCookies : 1;
+    mutable bool m_resourceRequestUpdated : 1;
+    mutable bool m_platformRequestUpdated : 1;
+    mutable bool m_resourceRequestBodyUpdated : 1;
+    mutable bool m_platformRequestBodyUpdated : 1;
+    bool m_hiddenFromInspector : 1;
+    bool m_isTopSite : 1;
 #if USE(SYSTEM_PREVIEW)
     Optional<SystemPreviewInfo> m_systemPreviewInfo;
 #endif

Modified: branches/safari-609-branch/Source/WebCore/platform/network/ResourceResponseBase.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/platform/network/ResourceResponseBase.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/platform/network/ResourceResponseBase.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -48,7 +48,9 @@
     WTF_MAKE_FAST_ALLOCATED;
 public:
     enum class Type : uint8_t { Basic, Cors, Default, Error, Opaque, Opaqueredirect };
+    static constexpr unsigned bitWidthOfType = 3;
     enum class Tainting : uint8_t { Basic, Cors, Opaque, Opaqueredirect };
+    static constexpr unsigned bitWidthOfTainting = 2;
 
     static bool isRedirectionStatusCode(int code) { return code == 301 || code == 302 || code == 303 || code == 307 || code == 308; }
 

Modified: branches/safari-609-branch/Source/WebCore/platform/network/StoredCredentialsPolicy.h (256690 => 256691)


--- branches/safari-609-branch/Source/WebCore/platform/network/StoredCredentialsPolicy.h	2020-02-15 03:02:33 UTC (rev 256690)
+++ branches/safari-609-branch/Source/WebCore/platform/network/StoredCredentialsPolicy.h	2020-02-15 03:02:39 UTC (rev 256691)
@@ -32,5 +32,6 @@
     Use,
     EphemeralStateless
 };
+static constexpr unsigned bitWidthOfStoredCredentialsPolicy = 2;
 
 } // namespace WebCore
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to