Bug 1323644 - Isolate the HSTS and HPKP storage by first party domain (Necko) r=mayhemer draft
authorJonathan Hao <jhao@mozilla.com>
Tue, 24 Jan 2017 12:07:32 +0800
changeset 465946 1886e9abf6a490b1ad4f688c28933d69822ee96b
parent 465945 17985b05d83dc6a126ca7b1e2793f6c5e3686516
child 465947 1fb59daa3d9197412d08979c8c44d034b49ae527
push id42762
push userbmo:jhao@mozilla.com
push dateWed, 25 Jan 2017 03:22:43 +0000
reviewersmayhemer
bugs1323644
milestone53.0a1
Bug 1323644 - Isolate the HSTS and HPKP storage by first party domain (Necko) r=mayhemer
netwerk/base/nsNetUtil.cpp
netwerk/protocol/http/HSTSPrimerListener.cpp
netwerk/protocol/http/nsHttpChannel.cpp
netwerk/protocol/http/nsHttpHandler.cpp
--- a/netwerk/base/nsNetUtil.cpp
+++ b/netwerk/base/nsNetUtil.cpp
@@ -2223,20 +2223,27 @@ NS_ShouldSecureUpgrade(nsIURI* aURI,
         return NS_OK;
       }
     }
 
     // enforce Strict-Transport-Security
     nsISiteSecurityService* sss = gHttpHandler->GetSSService();
     NS_ENSURE_TRUE(sss, NS_ERROR_OUT_OF_MEMORY);
 
+    OriginAttributes originAttributes;
+    if (aLoadInfo) {
+      originAttributes = aLoadInfo->GetOriginAttributes();
+    } else if (aChannelResultPrincipal) {
+      originAttributes.Inherit(aChannelResultPrincipal->OriginAttributesRef());
+    }
+
     bool isStsHost = false;
     uint32_t flags = aPrivateBrowsing ? nsISocketProvider::NO_PERMANENT_STORAGE : 0;
     rv = sss->IsSecureURI(nsISiteSecurityService::HEADER_HSTS, aURI, flags,
-                          nullptr, &isStsHost);
+                          originAttributes, nullptr, &isStsHost);
 
     // if the SSS check fails, it's likely because this load is on a
     // malformed URI or something else in the setup is wrong, so any error
     // should be reported.
     NS_ENSURE_SUCCESS(rv, rv);
 
     if (isStsHost) {
       LOG(("nsHttpChannel::Connect() STS permissions found\n"));
--- a/netwerk/protocol/http/HSTSPrimerListener.cpp
+++ b/netwerk/protocol/http/HSTSPrimerListener.cpp
@@ -141,18 +141,22 @@ HSTSPrimingListener::CheckHSTSPrimingReq
   nsCOMPtr<nsISiteSecurityService> sss = do_GetService(NS_SSSERVICE_CONTRACTID, &rv);
   NS_ENSURE_SUCCESS(rv, rv);
 
   nsCOMPtr<nsIURI> uri;
   rv = httpChannel->GetURI(getter_AddRefs(uri));
   NS_ENSURE_SUCCESS(rv, rv);
   NS_ENSURE_TRUE(uri, NS_ERROR_CONTENT_BLOCKED);
 
+  OriginAttributes originAttributes;
+  NS_GetOriginAttributes(httpChannel, originAttributes);
+
   bool hsts;
-  rv = sss->IsSecureURI(nsISiteSecurityService::HEADER_HSTS, uri, 0, nullptr, &hsts);
+  rv = sss->IsSecureURI(nsISiteSecurityService::HEADER_HSTS, uri, 0,
+                        originAttributes, nullptr, &hsts);
   NS_ENSURE_SUCCESS(rv, rv);
 
   if (hsts) {
     // An HSTS upgrade was found
     return NS_OK;
   }
 
   // There is no HSTS upgrade available
@@ -214,17 +218,22 @@ HSTSPrimingListener::StartHSTSPriming(ns
   rv = NS_GetSecureUpgradedURI(finalChannelURI, getter_AddRefs(uri));
   NS_ENSURE_SUCCESS(rv,rv);
 
   // check the HSTS cache
   bool hsts;
   bool cached;
   nsCOMPtr<nsISiteSecurityService> sss = do_GetService(NS_SSSERVICE_CONTRACTID, &rv);
   NS_ENSURE_SUCCESS(rv, rv);
-  rv = sss->IsSecureURI(nsISiteSecurityService::HEADER_HSTS, uri, 0, &cached, &hsts);
+
+  OriginAttributes originAttributes;
+  NS_GetOriginAttributes(aRequestChannel, originAttributes);
+
+  rv = sss->IsSecureURI(nsISiteSecurityService::HEADER_HSTS, uri, 0,
+                        originAttributes,&cached, &hsts);
   NS_ENSURE_SUCCESS(rv, rv);
 
   if (hsts) {
     // already saw this host and will upgrade if allowed by preferences
     return aCallback->OnHSTSPrimingSucceeded(true);
   }
 
   if (cached) {
--- a/netwerk/protocol/http/nsHttpChannel.cpp
+++ b/netwerk/protocol/http/nsHttpChannel.cpp
@@ -1575,19 +1575,22 @@ nsHttpChannel::ProcessSingleSecurityHead
 
     nsAutoCString securityHeader;
     nsresult rv = mResponseHead->GetHeader(atom, securityHeader);
     if (NS_SUCCEEDED(rv)) {
         nsISiteSecurityService* sss = gHttpHandler->GetSSService();
         NS_ENSURE_TRUE(sss, NS_ERROR_OUT_OF_MEMORY);
         // Process header will now discard the headers itself if the channel
         // wasn't secure (whereas before it had to be checked manually)
+        OriginAttributes originAttributes;
+        NS_GetOriginAttributes(this, originAttributes);
         uint32_t failureResult;
         rv = sss->ProcessHeader(aType, mURI, securityHeader, aSSLStatus,
-                                aFlags, nullptr, nullptr, &failureResult);
+                                aFlags, originAttributes, nullptr, nullptr,
+                                &failureResult);
         if (NS_FAILED(rv)) {
             nsAutoString consoleErrorCategory;
             nsAutoString consoleErrorTag;
             switch (aType) {
                 case nsISiteSecurityService::HEADER_HSTS:
                     GetSTSConsoleErrorTag(failureResult, consoleErrorTag);
                     consoleErrorCategory = NS_LITERAL_STRING("Invalid HSTS Headers");
                     break;
@@ -8104,18 +8107,20 @@ nsHttpChannel::OnHSTSPrimingFailed(nsres
                 (wouldBlock) ?  HSTSPrimingResult::eHSTS_PRIMING_FAILED_BLOCK :
                 HSTSPrimingResult::eHSTS_PRIMING_FAILED_ACCEPT);
     }
 
     // Don't visit again for at least
     // security.mixed_content.hsts_priming_cache_timeout seconds.
     nsISiteSecurityService* sss = gHttpHandler->GetSSService();
     NS_ENSURE_TRUE(sss, NS_ERROR_OUT_OF_MEMORY);
+    OriginAttributes originAttributes;
+    NS_GetOriginAttributes(this, originAttributes);
     nsresult rv = sss->CacheNegativeHSTSResult(mURI,
-            nsMixedContentBlocker::sHSTSPrimingCacheTimeout);
+            nsMixedContentBlocker::sHSTSPrimingCacheTimeout, originAttributes);
     if (NS_FAILED(rv)) {
         NS_ERROR("nsISiteSecurityService::CacheNegativeHSTSResult failed");
     }
 
     // If we would block, go ahead and abort with the error provided
     if (wouldBlock) {
         CloseCacheEntry(false);
         return AsyncAbort(aError);
--- a/netwerk/protocol/http/nsHttpHandler.cpp
+++ b/netwerk/protocol/http/nsHttpHandler.cpp
@@ -2252,19 +2252,32 @@ nsHttpHandler::SpeculativeConnectInterna
     bool isStsHost = false;
     if (!sss)
         return NS_OK;
 
     nsCOMPtr<nsILoadContext> loadContext = do_GetInterface(aCallbacks);
     uint32_t flags = 0;
     if (loadContext && loadContext->UsePrivateBrowsing())
         flags |= nsISocketProvider::NO_PERMANENT_STORAGE;
+
+    OriginAttributes originAttributes;
+    // If the principal is given, we use the originAttributes from this
+    // principal. Otherwise, we use the originAttributes from the
+    // loadContext.
+    if (aPrincipal) {
+        originAttributes.Inherit(aPrincipal->OriginAttributesRef());
+    } else if (loadContext) {
+        loadContext->GetOriginAttributes(originAttributes);
+        originAttributes.StripAttributes(OriginAttributes::STRIP_ADDON_ID);
+    }
+
     nsCOMPtr<nsIURI> clone;
     if (NS_SUCCEEDED(sss->IsSecureURI(nsISiteSecurityService::HEADER_HSTS,
-                                      aURI, flags, nullptr, &isStsHost)) &&
+                                      aURI, flags, originAttributes,
+                                      nullptr, &isStsHost)) &&
                                       isStsHost) {
         if (NS_SUCCEEDED(NS_GetSecureUpgradedURI(aURI,
                                                  getter_AddRefs(clone)))) {
             aURI = clone.get();
             // (NOTE: We better make sure |clone| stays alive until the end
             // of the function now, since our aURI arg now points to it!)
         }
     }
@@ -2300,27 +2313,16 @@ nsHttpHandler::SpeculativeConnectInterna
     int32_t port = -1;
     rv = aURI->GetPort(&port);
     if (NS_FAILED(rv))
         return rv;
 
     nsAutoCString username;
     aURI->GetUsername(username);
 
-    OriginAttributes originAttributes;
-    // If the principal is given, we use the originAttributes from this
-    // principal. Otherwise, we use the originAttributes from the
-    // loadContext.
-    if (aPrincipal) {
-        originAttributes.Inherit(aPrincipal->OriginAttributesRef());
-    } else if (loadContext) {
-        loadContext->GetOriginAttributes(originAttributes);
-        originAttributes.StripAttributes(OriginAttributes::STRIP_ADDON_ID);
-    }
-
     auto *ci =
         new nsHttpConnectionInfo(host, port, EmptyCString(), username, nullptr,
                                  originAttributes, usingSSL);
     ci->SetAnonymous(anonymous);
 
     return SpeculativeConnect(ci, aCallbacks);
 }