Backed out 1 changesets (bug 1005225) for Gu permared
authorWes Kocher <wkocher@mozilla.com>
Tue, 15 Jul 2014 16:18:50 -0700
changeset 216184 28dfed91343651e9958183f4ba9a88037f09985e
parent 216183 472e3405d85182be99fc4abdfb422c5c463b7221
child 216185 4bbe15384faa748131d0c248fbc5d89f705b5462
push id515
push userraliiev@mozilla.com
push dateMon, 06 Oct 2014 12:51:51 +0000
treeherdermozilla-release@267c7a481bef [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
bugs1005225, 1030936
milestone33.0a1
backs out452d8502bea14bcf6e08db0585bde526349182e2
32a1fa1b28d5bb9b43bd745af6cbcb485ef4fb9e
61d41b381f30647351387bdbbd77066d546e45cd
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Backed out 1 changesets (bug 1005225) for Gu permared Backed out changeset 452d8502bea1 (bug 1005225) * * * Backed out 2 changesets (bug 1005225, bug 1030936) for Gu permared Backed out changeset 32a1fa1b28d5 (bug 1030936) Backed out changeset 61d41b381f30 (bug 1005225)
content/base/public/nsIContentSecurityPolicy.idl
content/base/src/nsCSPContext.cpp
content/base/src/nsCSPService.cpp
--- a/content/base/public/nsIContentSecurityPolicy.idl
+++ b/content/base/public/nsIContentSecurityPolicy.idl
@@ -12,17 +12,17 @@ interface nsIPrincipal;
 
 /**
  * nsIContentSecurityPolicy
  * Describes an XPCOM component used to model and enforce CSPs.  Instances of
  * this class may have multiple policies within them, but there should only be
  * one of these per document/principal.
  */
 
-[scriptable, uuid(3e923bf6-a974-4f3b-91c4-b4fd48b37732)]
+[scriptable, uuid(15c409c5-ebf8-457c-a8dd-5b169ca0b218)]
 interface nsIContentSecurityPolicy : nsISerializable
 {
 
   /**
    * Set to true when the CSP has been read in and parsed and is ready to
    * enforce.  This is a barrier for the nsDocument so it doesn't load any
    * sub-content until either it knows that a CSP is ready or will not be used.
    */
@@ -216,14 +216,26 @@ interface nsIContentSecurityPolicy : nsI
    */
   short shouldLoad(in nsContentPolicyType aContentType,
                    in nsIURI          aContentLocation,
                    in nsIURI          aRequestOrigin,
                    in nsISupports     aContext,
                    in ACString        aMimeTypeGuess,
                    in nsISupports     aExtra);
 
+  /**
+   * Delegate method called by the service when sub-elements of the protected
+   * document are being processed.  Given a bit of information about the request,
+   * decides whether or not the policy is satisfied.
+   */
+  short shouldProcess(in nsContentPolicyType   aContentType,
+                      in nsIURI          aContentLocation,
+                      in nsIURI          aRequestOrigin,
+                      in nsISupports     aContext,
+                      in ACString        aMimeType,
+                      in nsISupports     aExtra);
+
 %{ C++
 // nsIObserver topic to fire when the policy encounters a violation.
 #define CSP_VIOLATION_TOPIC "csp-on-violate-policy"
 %}
 
 };
--- a/content/base/src/nsCSPContext.cpp
+++ b/content/base/src/nsCSPContext.cpp
@@ -204,16 +204,29 @@ nsCSPContext::ShouldLoad(nsContentPolicy
   nsAutoCString spec;
   aContentLocation->GetSpec(spec);
   CSPCONTEXTLOG(("nsCSPContext::ShouldLoad, decision: %s, aContentLocation: %s", *outDecision ? "load" : "deny", spec.get()));
   }
 #endif
   return NS_OK;
 }
 
+NS_IMETHODIMP
+nsCSPContext::ShouldProcess(nsContentPolicyType aContentType,
+                            nsIURI*             aContentLocation,
+                            nsIURI*             aRequestOrigin,
+                            nsISupports*        aRequestContext,
+                            const nsACString&   aMimeType,
+                            nsISupports*        aExtra,
+                            int16_t*            outDecision)
+{
+  *outDecision = nsIContentPolicy::ACCEPT;
+  return NS_OK;
+}
+
 /* ===== nsISupports implementation ========== */
 
 NS_IMPL_CLASSINFO(nsCSPContext,
                   nullptr,
                   nsIClassInfo::MAIN_THREAD_ONLY,
                   NS_CSPCONTEXT_CID)
 
 NS_IMPL_ISUPPORTS_CI(nsCSPContext,
--- a/content/base/src/nsCSPService.cpp
+++ b/content/base/src/nsCSPService.cpp
@@ -103,16 +103,65 @@ CSPService::ShouldLoad(uint32_t aContent
   // TYPE_CSP_REPORT, TYPE_REFRESH, TYPE_DOCUMENT
   // (their mappings are null in contentSecurityPolicy.js)
   if (aContentType == nsIContentPolicy::TYPE_CSP_REPORT ||
     aContentType == nsIContentPolicy::TYPE_REFRESH ||
     aContentType == nsIContentPolicy::TYPE_DOCUMENT) {
     return NS_OK;
   }
 
+  // ----- THIS IS A TEMPORARY FAST PATH FOR CERTIFIED APPS. -----
+  // ----- PLEASE REMOVE ONCE bug 925004 LANDS.              -----
+
+  // Cache the app status for this origin.
+  uint16_t status = nsIPrincipal::APP_STATUS_NOT_INSTALLED;
+  nsAutoCString contentOrigin;
+  aContentLocation->GetPrePath(contentOrigin);
+  if (aRequestPrincipal && !mAppStatusCache.Get(contentOrigin, &status)) {
+    aRequestPrincipal->GetAppStatus(&status);
+    mAppStatusCache.Put(contentOrigin, status);
+  }
+
+  if (status == nsIPrincipal::APP_STATUS_CERTIFIED) {
+    // The CSP for certified apps is :
+    // "default-src *; script-src 'self'; object-src 'none'; style-src 'self'"
+    // That means we can optimize for this case by:
+    // - loading only same origin scripts and stylesheets.
+    // - never loading objects.
+    // - accepting everything else.
+
+    switch (aContentType) {
+      case nsIContentPolicy::TYPE_SCRIPT:
+      case nsIContentPolicy::TYPE_STYLESHEET:
+        {
+          nsAutoCString sourceOrigin;
+          aRequestOrigin->GetPrePath(sourceOrigin);
+          if (!sourceOrigin.Equals(contentOrigin)) {
+            *aDecision = nsIContentPolicy::REJECT_SERVER;
+          }
+        }
+        break;
+
+      case nsIContentPolicy::TYPE_OBJECT:
+        *aDecision = nsIContentPolicy::REJECT_SERVER;
+        break;
+
+      default:
+        *aDecision = nsIContentPolicy::ACCEPT;
+    }
+
+    // Only cache and return if we are successful. If not, we want the error
+    // to be reported, and thus fallback to the slow path.
+    if (*aDecision == nsIContentPolicy::ACCEPT) {
+      return NS_OK;
+    }
+  }
+
+  // ----- END OF TEMPORARY FAST PATH FOR CERTIFIED APPS. -----
+
   // find the principal of the document that initiated this request and see
   // if it has a CSP policy object
   nsCOMPtr<nsINode> node(do_QueryInterface(aRequestContext));
   nsCOMPtr<nsIPrincipal> principal;
   nsCOMPtr<nsIContentSecurityPolicy> csp;
   if (node) {
     principal = node->NodePrincipal();
     principal->GetCsp(getter_AddRefs(csp));
@@ -164,17 +213,66 @@ CSPService::ShouldProcess(uint32_t      
                           const nsACString &aMimeTypeGuess,
                           nsISupports      *aExtra,
                           nsIPrincipal     *aRequestPrincipal,
                           int16_t          *aDecision)
 {
   if (!aContentLocation)
     return NS_ERROR_FAILURE;
 
+  // default decision is to accept the item
   *aDecision = nsIContentPolicy::ACCEPT;
+
+  // No need to continue processing if CSP is disabled
+  if (!sCSPEnabled)
+    return NS_OK;
+
+  // find the nsDocument that initiated this request and see if it has a
+  // CSP policy object
+  nsCOMPtr<nsINode> node(do_QueryInterface(aRequestContext));
+  nsCOMPtr<nsIPrincipal> principal;
+  nsCOMPtr<nsIContentSecurityPolicy> csp;
+  if (node) {
+    principal = node->NodePrincipal();
+    principal->GetCsp(getter_AddRefs(csp));
+
+    if (csp) {
+#ifdef PR_LOGGING
+      {
+        uint32_t numPolicies = 0;
+        nsresult rv = csp->GetPolicyCount(&numPolicies);
+        if (NS_SUCCEEDED(rv)) {
+          for (uint32_t i=0; i<numPolicies; i++) {
+            nsAutoString policy;
+            csp->GetPolicy(i, policy);
+            PR_LOG(gCspPRLog, PR_LOG_DEBUG,
+                   ("shouldProcess - document has policy[%d]: %s", i,
+                   NS_ConvertUTF16toUTF8(policy).get()));
+          }
+        }
+      }
+#endif
+      // obtain the enforcement decision
+      csp->ShouldProcess(aContentType,
+                         aContentLocation,
+                         aRequestOrigin,
+                         aRequestContext,
+                         aMimeTypeGuess,
+                         aExtra,
+                         aDecision);
+    }
+  }
+#ifdef PR_LOGGING
+  else {
+    nsAutoCString uriSpec;
+    aContentLocation->GetSpec(uriSpec);
+    PR_LOG(gCspPRLog, PR_LOG_DEBUG,
+           ("COULD NOT get nsINode for location: %s", uriSpec.get()));
+  }
+#endif
   return NS_OK;
 }
 
 /* nsIChannelEventSink implementation */
 NS_IMETHODIMP
 CSPService::AsyncOnChannelRedirect(nsIChannel *oldChannel,
                                    nsIChannel *newChannel,
                                    uint32_t flags,