Bug 1217070: Fix accessing the bootstrap methods when they are declared in the new lexical scope. r=rhelmer
authorDave Townsend <dtownsend@oxymoronical.com>
Wed, 21 Oct 2015 10:26:28 -0700
changeset 304488 ccb7bb578fb15e0fe344b0e9a3b3628faed8bedc
parent 304487 1bc27334b6ee6cf9003364d7ffd6147e9704267c
child 304489 a6eb8032ebf668d7baa2637190aadb39ed2a810e
push id1001
push userraliiev@mozilla.com
push dateMon, 18 Jan 2016 19:06:03 +0000
treeherdermozilla-release@8b89261f3ac4 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersrhelmer
bugs1217070
milestone44.0a1
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
Bug 1217070: Fix accessing the bootstrap methods when they are declared in the new lexical scope. r=rhelmer Rather that trying to get the method from the sandbox global object which will only work for var and function declared methods instead evaluate the function name in the sandbox scope and get the result which will give us access to the lexical scope.
toolkit/mozapps/extensions/internal/XPIProvider.jsm
toolkit/mozapps/extensions/test/addons/test_bootstrap_const/bootstrap.js
toolkit/mozapps/extensions/test/addons/test_bootstrap_const/install.rdf
toolkit/mozapps/extensions/test/xpcshell/test_bootstrap_const.js
toolkit/mozapps/extensions/test/xpcshell/xpcshell-shared.ini
toolkit/mozapps/extensions/test/xpcshell/xpcshell.ini
--- a/toolkit/mozapps/extensions/internal/XPIProvider.jsm
+++ b/toolkit/mozapps/extensions/internal/XPIProvider.jsm
@@ -4352,17 +4352,28 @@ this.XPIProvider = {
                                 aAddon.multiprocessCompatible || false,
                                 runInSafeMode);
       }
 
       // Nothing to call for locales
       if (aAddon.type == "locale")
         return;
 
-      if (!(aMethod in this.bootstrapScopes[aAddon.id])) {
+      let method = undefined;
+      try {
+        method = Components.utils.evalInSandbox(`${aMethod};`,
+                                                this.bootstrapScopes[aAddon.id],
+                                                "ECMAv5");
+      }
+      catch (e) {
+        // An exception will be caught if the expected method is not defined.
+        // That will be logged below.
+      }
+
+      if (!method) {
         logger.warn("Add-on " + aAddon.id + " is missing bootstrap method " + aMethod);
         return;
       }
 
       let params = {
         id: aAddon.id,
         version: aAddon.version,
         installPath: aFile.clone(),
@@ -4371,19 +4382,19 @@ this.XPIProvider = {
 
       if (aExtraParams) {
         for (let key in aExtraParams) {
           params[key] = aExtraParams[key];
         }
       }
 
       logger.debug("Calling bootstrap method " + aMethod + " on " + aAddon.id + " version " +
-          aAddon.version);
+                   aAddon.version);
       try {
-        this.bootstrapScopes[aAddon.id][aMethod](params, aReason);
+        method(params, aReason);
       }
       catch (e) {
         logger.warn("Exception running bootstrap method " + aMethod + " on " + aAddon.id, e);
       }
     }
     finally {
       if (CHROME_TYPES.has(aAddon.type) && aMethod == "shutdown" && aReason != BOOTSTRAP_REASONS.APP_SHUTDOWN) {
         logger.debug("Removing manifest for " + aFile.path);
new file mode 100644
--- /dev/null
+++ b/toolkit/mozapps/extensions/test/addons/test_bootstrap_const/bootstrap.js
@@ -0,0 +1,5 @@
+Components.utils.import("resource://gre/modules/Services.jsm");
+
+const install = function() {
+  Services.obs.notifyObservers(null, "addon-install", "");
+}
new file mode 100644
--- /dev/null
+++ b/toolkit/mozapps/extensions/test/addons/test_bootstrap_const/install.rdf
@@ -0,0 +1,24 @@
+<?xml version="1.0"?>
+
+<RDF xmlns="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
+     xmlns:em="http://www.mozilla.org/2004/em-rdf#">
+
+  <Description about="urn:mozilla:install-manifest">
+    <em:id>bootstrap@tests.mozilla.org</em:id>
+    <em:version>1.0</em:version>
+    <em:bootstrap>true</em:bootstrap>
+
+    <!-- Front End MetaData -->
+    <em:name>Test Bootstrap</em:name>
+    <em:description>Test Description</em:description>
+
+    <em:targetApplication>
+      <Description>
+        <em:id>xpcshell@tests.mozilla.org</em:id>
+        <em:minVersion>1</em:minVersion>
+        <em:maxVersion>1</em:maxVersion>
+      </Description>
+    </em:targetApplication>
+
+  </Description>
+</RDF>
new file mode 100644
--- /dev/null
+++ b/toolkit/mozapps/extensions/test/xpcshell/test_bootstrap_const.js
@@ -0,0 +1,17 @@
+/* Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/publicdomain/zero/1.0/
+ */
+
+createAppInfo("xpcshell@tests.mozilla.org", "XPCShell", "1", "1");
+startupManager();
+
+add_task(function*() {
+  let sawInstall = false;
+  Services.obs.addObserver(function() {
+    sawInstall = true;
+  }, "addon-install", false);
+
+  yield promiseInstallAllFiles([do_get_addon("test_bootstrap_const")]);
+
+  ok(sawInstall);
+});
--- a/toolkit/mozapps/extensions/test/xpcshell/xpcshell-shared.ini
+++ b/toolkit/mozapps/extensions/test/xpcshell/xpcshell-shared.ini
@@ -25,16 +25,17 @@ requesttimeoutfactor = 2
 [test_blocklist_metadata_filters.js]
 # Bug 676992: test consistently hangs on Android
 skip-if = os == "android"
 [test_blocklist_regexp.js]
 skip-if = os == "android"
 [test_bootstrap.js]
 # Bug 676992: test consistently hangs on Android
 skip-if = os == "android"
+[test_bootstrap_const.js]
 [test_bootstrap_resource.js]
 [test_bug299716.js]
 # Bug 676992: test consistently hangs on Android
 skip-if = os == "android"
 run-sequentially = Uses hardcoded ports in xpi files.
 [test_bug299716_2.js]
 # Bug 676992: test consistently hangs on Android
 skip-if = os == "android"
--- a/toolkit/mozapps/extensions/test/xpcshell/xpcshell.ini
+++ b/toolkit/mozapps/extensions/test/xpcshell/xpcshell.ini
@@ -25,9 +25,10 @@ skip-if = appname != "firefox"
 [test_provider_unsafe_access_startup.js]
 [test_ProductAddonChecker.js]
 [test_shutdown.js]
 [test_system_update.js]
 [test_system_reset.js]
 [test_XPIcancel.js]
 [test_XPIStates.js]
 
+
 [include:xpcshell-shared.ini]