Bug 1072152 - Change chrome.manifest read order. r=bsmedberg
authorMike Hommey <mh+mozilla@glandium.org>
Thu, 25 Sep 2014 14:47:03 +0900
changeset 207366 e9d7f94062a92f913e93b52e2af6ce0aae2b8e9f
parent 207365 e2fee324047ddeebc5045a7fc474450141b92b0f
child 207367 72e22f3d7cc62cef70875e03e83f971fd3be182a
push idunknown
push userunknown
push dateunknown
reviewersbsmedberg
bugs1072152
milestone35.0a1
Bug 1072152 - Change chrome.manifest read order. r=bsmedberg In case of multiple "resource" manifest entries for the same keyword, the last registered one now takes precedence, like any other chrome manifest entry.
chrome/nsChromeRegistryChrome.cpp
chrome/test/unit/data/test_bug401153.manifest
toolkit/components/addoncompat/RemoteAddonsParent.jsm
xpcom/components/nsComponentManager.cpp
--- a/chrome/nsChromeRegistryChrome.cpp
+++ b/chrome/nsChromeRegistryChrome.cpp
@@ -991,24 +991,16 @@ nsChromeRegistryChrome::ManifestResource
 
   nsCOMPtr<nsIProtocolHandler> ph;
   nsresult rv = io->GetProtocolHandler("resource", getter_AddRefs(ph));
   if (NS_FAILED(rv))
     return;
 
   nsCOMPtr<nsIResProtocolHandler> rph = do_QueryInterface(ph);
 
-  bool exists = false;
-  rv = rph->HasSubstitution(host, &exists);
-  if (exists) {
-    LogMessageWithContext(cx.GetManifestURI(), lineno, nsIScriptError::warningFlag,
-                          "Duplicate resource declaration for '%s' ignored.", package);
-    return;
-  }
-
   nsCOMPtr<nsIURI> resolved = cx.ResolveURI(uri);
   if (!resolved) {
     LogMessageWithContext(cx.GetManifestURI(), lineno, nsIScriptError::warningFlag,
                           "During chrome registration, unable to create URI '%s'.", uri);
     return;
   }
 
   if (!CanLoadResource(resolved)) {
--- a/chrome/test/unit/data/test_bug401153.manifest
+++ b/chrome/test/unit/data/test_bug401153.manifest
@@ -1,14 +1,11 @@
 # Should work
 resource test1 test1/
 
-# Duplicates should be ignored
-resource test1 foo/
-
 # Mapping into jar files should work
 resource test3 jar:test3.jar!/resources/
 
 # Invalid line
 resource test4
 
 # Check we made it through the whole manifest
 resource test5 test5/
--- a/toolkit/components/addoncompat/RemoteAddonsParent.jsm
+++ b/toolkit/components/addoncompat/RemoteAddonsParent.jsm
@@ -257,17 +257,17 @@ ComponentRegistrarInterposition.methods.
       AboutProtocolParent.registerFactory(class_, className, contractID, factory);
     }
 
     target.registerFactory(class_, className, contractID, factory);
   };
 
 ComponentRegistrarInterposition.methods.unregisterFactory =
   function(addon, target, class_, factory) {
-    AboutProtocolParent.tryUnregisterFactory(class_, factory);
+    AboutProtocolParent.unregisterFactory(class_, factory);
     target.unregisterFactory(class_, factory);
   };
 
 // This object manages add-on observers that might fire in the child
 // process. Rather than managing the observers itself, it uses the
 // parent's observer service. When an add-on listens on topic T,
 // ObserverParent asks the child process to listen on T. It also adds
 // an observer in the parent for the topic e10s-T. When the T observer
--- a/xpcom/components/nsComponentManager.cpp
+++ b/xpcom/components/nsComponentManager.cpp
@@ -369,76 +369,84 @@ nsComponentManagerImpl::Init()
   PL_INIT_ARENA_POOL(&mArena, "ComponentManagerArena", NS_CM_BLOCK_SIZE);
 
   nsCOMPtr<nsIFile> greDir =
     GetLocationFromDirectoryService(NS_GRE_DIR);
   nsCOMPtr<nsIFile> appDir =
     GetLocationFromDirectoryService(NS_XPCOM_CURRENT_PROCESS_DIR);
 
   InitializeStaticModules();
-  InitializeModuleLocations();
-
-  ComponentLocation* cl = sModuleLocations->InsertElementAt(0);
-  nsCOMPtr<nsIFile> lf = CloneAndAppend(appDir,
-                                        NS_LITERAL_CSTRING("chrome.manifest"));
-  cl->type = NS_COMPONENT_LOCATION;
-  cl->location.Init(lf);
-
-  bool equals = false;
-  appDir->Equals(greDir, &equals);
-  if (!equals) {
-    cl = sModuleLocations->InsertElementAt(0);
-    cl->type = NS_COMPONENT_LOCATION;
-    lf = CloneAndAppend(greDir, NS_LITERAL_CSTRING("chrome.manifest"));
-    cl->location.Init(lf);
-  }
-
-  PR_LOG(nsComponentManagerLog, PR_LOG_DEBUG,
-         ("nsComponentManager: Initialized."));
 
   nsresult rv = mNativeModuleLoader.Init();
   if (NS_FAILED(rv)) {
     return rv;
   }
 
   nsCategoryManager::GetSingleton()->SuppressNotifications(true);
 
   RegisterModule(&kXPCOMModule, nullptr);
 
   for (uint32_t i = 0; i < sStaticModules->Length(); ++i) {
     RegisterModule((*sStaticModules)[i], nullptr);
   }
 
+  // The overall order in which chrome.manifests are expected to be treated
+  // is the following:
+  // - greDir
+  // - greDir's omni.ja
+  // - appDir
+  // - appDir's omni.ja
+
+  InitializeModuleLocations();
+  ComponentLocation* cl = sModuleLocations->AppendElement();
+  nsCOMPtr<nsIFile> lf = CloneAndAppend(greDir,
+                                        NS_LITERAL_CSTRING("chrome.manifest"));
+  cl->type = NS_COMPONENT_LOCATION;
+  cl->location.Init(lf);
+
+  nsRefPtr<nsZipArchive> greOmnijar =
+    mozilla::Omnijar::GetReader(mozilla::Omnijar::GRE);
+  if (greOmnijar) {
+    cl = sModuleLocations->AppendElement();
+    cl->type = NS_COMPONENT_LOCATION;
+    cl->location.Init(greOmnijar, "chrome.manifest");
+  }
+
+  bool equals = false;
+  appDir->Equals(greDir, &equals);
+  if (!equals) {
+    cl = sModuleLocations->AppendElement();
+    cl->type = NS_COMPONENT_LOCATION;
+    lf = CloneAndAppend(appDir, NS_LITERAL_CSTRING("chrome.manifest"));
+    cl->location.Init(lf);
+  }
+
   nsRefPtr<nsZipArchive> appOmnijar =
     mozilla::Omnijar::GetReader(mozilla::Omnijar::APP);
   if (appOmnijar) {
-    cl = sModuleLocations->InsertElementAt(1); // Insert after greDir
+    cl = sModuleLocations->AppendElement();
     cl->type = NS_COMPONENT_LOCATION;
     cl->location.Init(appOmnijar, "chrome.manifest");
   }
-  nsRefPtr<nsZipArchive> greOmnijar =
-    mozilla::Omnijar::GetReader(mozilla::Omnijar::GRE);
-  if (greOmnijar) {
-    cl = sModuleLocations->InsertElementAt(0);
-    cl->type = NS_COMPONENT_LOCATION;
-    cl->location.Init(greOmnijar, "chrome.manifest");
-  }
 
   RereadChromeManifests(false);
 
   nsCategoryManager::GetSingleton()->SuppressNotifications(false);
 
   RegisterWeakMemoryReporter(this);
 
   // Unfortunately, we can't register the nsCategoryManager memory reporter
   // in its constructor (which is triggered by the GetSingleton() call
   // above) because the memory reporter manager isn't initialized at that
   // point.  So we wait until now.
   nsCategoryManager::GetSingleton()->InitMemoryReporter();
 
+  PR_LOG(nsComponentManagerLog, PR_LOG_DEBUG,
+         ("nsComponentManager: Initialized."));
+
   mStatus = NORMAL;
 
   return NS_OK;
 }
 
 void
 nsComponentManagerImpl::RegisterModule(const mozilla::Module* aModule,
                                        FileLocation* aFile)