How to force install an unverified firefox extension in 41.0b1+?

15

6

The latest update to Firefox (41.0b1) aggressively blocks the installation of unverified extensions, namely HTTPS Everywhere and Privacy Badger.

How might I be able to force these extensions to install? Is there a setting inside about:config I could temporarily toggle?

Mozilla highlights this change to Firefox here, noting its previous efforts to be inefficient at corralling malicious extensions.

VitaminYes

Posted 2015-08-12T19:24:56.580

Reputation: 1 275

Answers

19

Yes, there is a setting in About:config, its name is xpinstall.signatures.required. Double-click on the preference name so that its value is set to false. Now you can install unsigned extensions in Firefox. A browser restart is not needed.

Suzana

Posted 2015-08-12T19:24:56.580

Reputation: 399

2Fantastic! This fix will suffice until EFF and others have there extensions verified. – VitaminYes – 2015-08-12T21:02:29.083

1This also won't work after version 43+. :( – Suresh Atta – 2016-08-06T19:47:55.490

Despite many sources saying it won't work in recent FF, it worked for me in 48.0 on Linux. I had to open the addons page and drag the xpi file there. – That Brazilian Guy – 2016-08-09T13:51:17.847

@ThatBrazilianGato: is is not working for me on Win7 FF48.0 :( – glavić – 2016-08-16T13:37:42.827

In release notes for FF 48.0 it says: Add-ons that have not been verified and signed by Mozilla will not load

– glavić – 2016-08-16T13:41:08.343

Firefox 48: (Pushed from Firefox 46). Release and Beta versions of Firefox for Desktop will not allow unsigned extensions to be installed, with no override. Firefox for Android will enforce add-on signing, and will retain a preference — which will be removed in a future release — to allow the user to disable signing enforcement. – glavić – 2016-08-16T13:42:51.263

4That's it for me. Bye Firefox, loved you since version 0.6. :-( Hope there will be a workaround some day. – andreas – 2016-08-30T21:59:18.183

Firefox has been known for its crazy amount of malicious add-ons over which it seems to have little control. For a basic user, it becomes a nightmare. For a tech person, it becomes an oft-vanquished enemy. – Arlen Beiler – 2017-07-11T20:14:51.890

2

On Firefox 48 and above, this method doesn't work. Instead you should create two config files inside Firefox directory.

  1. Create config.js file in notepad (make sure file extension is .js and not .txt):

    //
    try {
    Components.utils.import("resource://gre/modules/addons/XPIProvider.jsm", {})
    .eval("SIGNED_TYPES.clear()");
    }
    catch(ex) {}
    
  2. Move config.js to your Firefox installation directory:

    Windows: C:\Program Files\Mozilla Firefox
    (or C:\Program Files (x86)\Mozilla Firefox )

    Linux: /usr/lib64/firefox-< version >
    (or /usr/lib/firefox-< version > )

    Mac: /Applications/Firefox.app

  3. Create config-prefs.js in notepad:

    pref("general.config.obscure_value", 0);
    pref("general.config.filename", "config.js");
    
  4. Move config-prefs.js into Firefox defaults\pref directory.
    (e.g. C:\Program Files\Mozilla Firefox\defaults\pref)

  5. Restart Firefox.

  6. Drag the unsigned XPI into Firefox window, or use the "Install Add-on From File" option, in the settings of Firefox Add-ons.


Originate from this source: https://forum.mozilla-russia.org/viewtopic.php?id=70326

Noam Manos

Posted 2015-08-12T19:24:56.580

Reputation: 771

Unfortunately this method doesn't seem to work on FF 66.0.3 64-bit. It'd be sorely needed now that Mozilla has messed up BIG time. – CoolKoon – 2019-05-04T19:24:09.150

1

Apparently on Firefox 60 and above neither the xpinstall.signatures.required nor the config.js trick outlined above works (Mozilla, keel over please!).

The Russian forum that's referenced above apparently mentions a solution for these versions of Firefox as well. So put this into config.js instead which you then save to C:\Program Files\Mozilla Firefox

//
try {(code => {
    var {classes: Cc, interfaces: Ci, utils: Cu} = Components;
    var jsval, evl = true, re = e => Cu.reportError(e), imp = name => {try {
        return Cu.import(`resource://gre/modules/addons/${name}.jsm`, {});
    } catch(ex) {}}
    if ((jsval = imp("AddonSettings"))) {
        jsval.AddonSettings = {ADDON_SIGNING: false, REQUIRE_SIGNING: false, ALLOW_LEGACY_EXTENSIONS: true};
        try {evl = jsval.eval("this") === jsval;} catch(ex) {evl = false;}
    }
    var jsvals = ["XPIProvider", "XPIInstall"].map(imp).filter(i => i);
    jsvals[0].AddonSettings && lockPref("extensions.allow-non-mpc-extensions", true);
    jsvals[0].signaturesNotRequired = true;

    if (evl) return jsvals.forEach(jsval => {try {jsval.eval(code);} catch(ex) {re(ex);}});

    var sl = Cc["@mozilla.org/moz/jssubscript-loader;1"].getService(Ci.mozIJSSubScriptLoader);
    Cu.importGlobalProperties(["URL", "Blob"]); var url = URL.createObjectURL(new Blob([(code)]));
    jsvals.forEach(jsval => {try {sl.loadSubScript(url, jsval);} catch(ex) {re(ex);}});

})(String.raw`((vzss, pckg) => {
    var trueDesc = {enumerable: true, value: true};
    typeof Extension == "function" && Object.defineProperty(Extension.prototype, "experimentsAllowed", trueDesc);
    "AddonInternal" in this && Object.defineProperty(AddonInternal.prototype, "providesUpdatesSecurely", trueDesc);
    this.isDisabledLegacy = () => false;
    if ("XPIDatabase" in this) this.XPIDatabase.isDisabledLegacy = () => false;
    try {SIGNED_TYPES.clear();} catch(ex) {};

    if (!vzss && !pckg) return;

    var re = /\x06\x03U\x04\x03..(\{[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}\}|[a-z0-9-\._]*\@[a-z0-9-\._]+)0\x82\x02"0\r\x06\t/i;
    var getUUID = () => {
        var gen = Cc["@mozilla.org/uuid-generator;1"].getService(Ci.nsIUUIDGenerator);
        return (getUUID = () => gen.generateUUID().toString())();
    }
    var getIdFromString = str => {
        var match = str && str.match(re);
        return match ? match[1] : getUUID();
    }
    var getState = arg => ({
        signedState: AddonManager.SIGNEDSTATE_NOT_REQUIRED,
        cert: typeof arg == "object" ? arg : {commonName: arg}
    });
    var checkAddon = addon => {
        if (addon.id || (
            "_installLocation" in addon
                ? addon._installLocation.name == KEY_APP_TEMPORARY
                : addon.location.isTemporary
        ))
            return getState(null);
    }
    var getRoot = () =>
        !AppConstants.MOZ_REQUIRE_SIGNING && Services.prefs.getBoolPref(PREF_XPI_SIGNATURES_DEV_ROOT, false)
            ? Ci.nsIX509CertDB.AddonsStageRoot : Ci.nsIX509CertDB.AddonsPublicRoot;

    if (vzss) {
        var getURI = file => {
            var jsval = Cu.import("resource://gre/modules/addons/XPIProvider.jsm", {});
            return (getURI = file => jsval.getURIForResourceInFile(file, "META-INF/mozilla.rsa"))(file);
        }
        var getIdFromFile = file => {
            var str, is = {close() {}}, sis = {close() {}};
            try {
                is = Services.io.newChannelFromURIWithLoadInfo(getURI(file), null).open();
                sis = Cc["@mozilla.org/scriptableinputstream;1"].createInstance(Ci.nsIScriptableInputStream);
                sis.init(is);
                str = sis.readBytes(sis.available());
            } catch(ex) {}
            sis.close(); is.close();
            return getIdFromString(str);
        }
        this.verifyZipSignedState = function verifyZipSignedState(aFile, aAddon) {
            var res = checkAddon(aAddon);
            return res ? Promise.resolve(res) : new Promise(resolve => {
                var callback = {openSignedAppFileFinished(rv, zipReader, cert) {
                    zipReader && zipReader.close();
                    resolve(getState(cert || getIdFromFile(aFile)));
                }};
                gCertDB.openSignedAppFileAsync(getRoot(), aFile, callback.wrappedJSObject = callback);
            });
        }
    }

    if (pckg) Package.prototype.verifySignedState = function verifySignedState(addon) {
        var res = checkAddon(addon);
        return res ? Promise.resolve(res) : new Promise(resolve =>
            this.verifySignedStateForRoot(addon, getRoot()).then(({cert}) => {
                if (cert)
                    resolve(getState(cert));
                else
                    this.readBinary("META-INF", "mozilla.rsa").then(
                        buffer => resolve(getState(
                            getIdFromString(String.fromCharCode(...new Uint8Array(buffer)))
                        )),
                        () => resolve(getState(getUUID()))
                    );
            }, Cu.reportError)
        );
    }
})(
    "verifyZipSignedState" in this, typeof Package == "function"
);`)} catch(err) {
    err.message != "Components is not defined" && Components.utils.reportError(err);
}

Then you have to add this to the config-prefs.js file saved to C:\Program Files\Mozilla Firefox\defaults\pref

pref("general.config.obscure_value", 0);
pref("general.config.filename", "config.js");
pref("general.config.sandbox_enabled", false);

It's been tested to work on FF 66.0.3. Unfortunately it won't bring your addons and themes magically back, but at least it re-enables the option of re-installing them. Better than anything Mozilla has to offer anyway, as they don't seem to particularly care despite the fact that their forums are being flooded with complaints about this problem.

CoolKoon

Posted 2015-08-12T19:24:56.580

Reputation: 111

Look, if you really really want this, don't install random hacks, just use a Nightly where the signatures.required preference string is actually enabled. – Félix Saparelli – 2019-05-05T10:18:21.550

1And why should I? Up until now I was completely fine with using what I thought to be stable versions of FF where I only installed legitimate and genuine addons straight from Firefox's official addon site. And now all these addons (and themes, for Christ's sake!) have stopped working all of a sudden. I'm sorry but instead of installing a potentially even more broken version of FF I prefer something that makes my current installation work instead. – CoolKoon – 2019-05-05T20:05:42.830

P.S. The addons have stopped working on the Android version of FF (v66.0.2) running on my phone as well, but curiously enough the xpinstall.signatures.required still seems to work there. – CoolKoon – 2019-05-05T20:08:38.103