Bug 950417 - Enable safe direct request add-on installs. r=wesj, r=Mossop

This commit is contained in:
Eugen Sawin 2014-03-19 21:24:59 +01:00
Родитель efe59c5d9b
Коммит a206a9418d
9 изменённых файлов: 183 добавлений и 5 удалений

Просмотреть файл

@ -170,6 +170,8 @@ pref("dom.experimental_forms", true);
pref("dom.forms.number", true);
/* extension manager and xpinstall */
pref("xpinstall.whitelist.directRequest", false);
pref("xpinstall.whitelist.fileRequest", false);
pref("xpinstall.whitelist.add", "addons.mozilla.org");
pref("xpinstall.whitelist.add.180", "marketplace.firefox.com");

Просмотреть файл

@ -141,6 +141,25 @@
<action android:name="android.intent.action.SEARCH" />
</intent-filter>
<!-- For XPI installs from websites and the download manager. -->
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<data android:scheme="file" />
<data android:scheme="http" />
<data android:scheme="https" />
<data android:mimeType="application/x-xpinstall" />
</intent-filter>
<!-- For XPI installs from file: URLs. -->
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<data android:host="" />
<data android:scheme="file" />
<data android:pathPattern=".*\\.xpi" />
</intent-filter>
#ifdef MOZ_ANDROID_BEAM
<intent-filter>
<action android:name="android.nfc.action.NDEF_DISCOVERED"/>

Просмотреть файл

@ -5695,7 +5695,10 @@ var XPInstallObserver = {
if (!tab)
return;
let host = installInfo.originatingURI.host;
let host = null;
if (installInfo.originatingURI) {
host = installInfo.originatingURI.host;
}
let brandShortName = Strings.brand.GetStringFromName("brandShortName");
let notificationName, buttons, message;
@ -5723,7 +5726,23 @@ var XPInstallObserver = {
}
} else {
notificationName = "xpinstall";
message = strings.formatStringFromName("xpinstallPromptWarning2", [brandShortName, host], 2);
if (host) {
// We have a host which asked for the install.
message = strings.formatStringFromName("xpinstallPromptWarning2", [brandShortName, host], 2);
} else {
// Without a host we address the add-on as the initiator of the install.
let addon = null;
if (installInfo.installs.length > 0) {
addon = installInfo.installs[0].name;
}
if (addon) {
// We have an addon name, show the regular message.
message = strings.formatStringFromName("xpinstallPromptWarningLocal", [brandShortName, addon], 2);
} else {
// We don't have an addon name, show an alternative message.
message = strings.formatStringFromName("xpinstallPromptWarningDirect", [brandShortName], 1);
}
}
buttons = [{
label: strings.GetStringFromName("xpinstallPromptAllowButton"),

Просмотреть файл

@ -71,6 +71,8 @@ blockPopups.label=Block Popups
# XPInstall
xpinstallPromptWarning2=%S prevented this site (%S) from asking you to install software on your device.
xpinstallPromptWarningLocal=%S prevented this add-on (%S) from installing on your device.
xpinstallPromptWarningDirect=%S prevented an add-on from installing on your device.
xpinstallPromptAllowButton=Allow
xpinstallDisabledMessageLocked=Software installation has been disabled by your system administrator.
xpinstallDisabledMessage2=Software installation is currently disabled. Press Enable and try again.

Просмотреть файл

@ -67,6 +67,8 @@ const PREF_EM_AUTO_DISABLED_SCOPES = "extensions.autoDisableScopes";
const PREF_EM_SHOW_MISMATCH_UI = "extensions.showMismatchUI";
const PREF_XPI_ENABLED = "xpinstall.enabled";
const PREF_XPI_WHITELIST_REQUIRED = "xpinstall.whitelist.required";
const PREF_XPI_DIRECT_WHITELISTED = "xpinstall.whitelist.directRequest";
const PREF_XPI_FILE_WHITELISTED = "xpinstall.whitelist.fileRequest";
const PREF_XPI_PERMISSIONS_BRANCH = "xpinstall.";
const PREF_XPI_UNPACK = "extensions.alwaysUnpack";
const PREF_INSTALL_REQUIREBUILTINCERTS = "extensions.install.requireBuiltInCerts";
@ -3445,6 +3447,28 @@ var XPIProvider = {
return Prefs.getBoolPref(PREF_XPI_ENABLED, true);
},
/**
* Called to test whether installing XPI add-ons by direct URL requests is
* whitelisted.
*
* @return true if installing by direct requests is whitelisted
*/
isDirectRequestWhitelisted: function XPI_isDirectRequestWhitelisted() {
// Default to whitelisted if the preference does not exist.
return Prefs.getBoolPref(PREF_XPI_DIRECT_WHITELISTED, true);
},
/**
* Called to test whether installing XPI add-ons from file referrers is
* whitelisted.
*
* @return true if installing from file referrers is whitelisted
*/
isFileRequestWhitelisted: function XPI_isFileRequestWhitelisted() {
// Default to whitelisted if the preference does not exist.
return Prefs.getBoolPref(PREF_XPI_FILE_WHITELISTED, true);
},
/**
* Called to test whether installing XPI add-ons from a URI is allowed.
*
@ -3456,11 +3480,13 @@ var XPIProvider = {
if (!this.isInstallEnabled())
return false;
// Direct requests without a referrer are either whitelisted or blocked.
if (!aUri)
return true;
return this.isDirectRequestWhitelisted();
// file: and chrome: don't need whitelisted hosts
if (aUri.schemeIs("chrome") || aUri.schemeIs("file"))
// Local referrers can be whitelisted.
if (this.isFileRequestWhitelisted() &&
(aUri.schemeIs("chrome") || aUri.schemeIs("file")))
return true;
this.importPermissions();

Просмотреть файл

@ -62,6 +62,8 @@ support-files =
[browser_installchrome.js]
[browser_localfile.js]
[browser_localfile2.js]
[browser_localfile3.js]
[browser_localfile4.js]
[browser_multipackage.js]
[browser_navigateaway.js]
[browser_navigateaway2.js]
@ -84,3 +86,4 @@ support-files =
[browser_whitelist4.js]
[browser_whitelist5.js]
[browser_whitelist6.js]
[browser_whitelist7.js]

Просмотреть файл

@ -0,0 +1,37 @@
// ----------------------------------------------------------------------------
// Tests installing an add-on from a local file with whitelisting disabled.
// This should be blocked by the whitelist check.
function test() {
Harness.installBlockedCallback = allow_blocked;
Harness.installsCompletedCallback = finish_test;
Harness.setup();
// Disable direct request whitelisting, installing from file should be blocked.
Services.prefs.setBoolPref("xpinstall.whitelist.directRequest", false);
var cr = Components.classes["@mozilla.org/chrome/chrome-registry;1"]
.getService(Components.interfaces.nsIChromeRegistry);
var chromeroot = extractChromeRoot(gTestPath);
try {
var xpipath = cr.convertChromeURL(makeURI(chromeroot + "unsigned.xpi")).spec;
} catch (ex) {
var xpipath = chromeroot + "unsigned.xpi"; //scenario where we are running from a .jar and already extracted
}
gBrowser.selectedTab = gBrowser.addTab();
gBrowser.loadURI(xpipath);
}
function allow_blocked(installInfo) {
ok(true, "Seen blocked");
return false;
}
function finish_test(count) {
is(count, 0, "No add-ons should have been installed");
Services.prefs.clearUserPref("xpinstall.whitelist.directRequest");
gBrowser.removeCurrentTab();
Harness.finish();
}

Просмотреть файл

@ -0,0 +1,40 @@
// ----------------------------------------------------------------------------
// Tests installing an add-on from a local file with whitelisting disabled.
// This should be blocked by the whitelist check.
function test() {
Harness.installBlockedCallback = allow_blocked;
Harness.installsCompletedCallback = finish_test;
Harness.setup();
// Disable file request whitelisting, installing by file referrer should be blocked.
Services.prefs.setBoolPref("xpinstall.whitelist.fileRequest", false);
var cr = Components.classes["@mozilla.org/chrome/chrome-registry;1"]
.getService(Components.interfaces.nsIChromeRegistry);
var chromeroot = extractChromeRoot(gTestPath);
try {
var xpipath = cr.convertChromeURL(makeURI(chromeroot)).spec;
} catch (ex) {
var xpipath = chromeroot; //scenario where we are running from a .jar and already extracted
}
var triggers = encodeURIComponent(JSON.stringify({
"Unsigned XPI": TESTROOT + "unsigned.xpi"
}));
gBrowser.selectedTab = gBrowser.addTab();
gBrowser.loadURI(xpipath + "installtrigger.html?" + triggers);
}
function allow_blocked(installInfo) {
ok(true, "Seen blocked");
return false;
}
function finish_test(count) {
is(count, 0, "No add-ons should have been installed");
Services.prefs.clearUserPref("xpinstall.whitelist.fileRequest");
gBrowser.removeCurrentTab();
Harness.finish();
}

Просмотреть файл

@ -0,0 +1,30 @@
// ----------------------------------------------------------------------------
// Tests installing an unsigned add-on through a direct install request from
// web content. This should be blocked by the whitelist check because we disable
// direct request whitelisting, even though the target URI is whitelisted.
function test() {
Harness.installBlockedCallback = allow_blocked;
Harness.installsCompletedCallback = finish_test;
Harness.setup();
// Disable direct request whitelisting, installing should be blocked.
Services.prefs.setBoolPref("xpinstall.whitelist.directRequest", false);
gBrowser.selectedTab = gBrowser.addTab();
gBrowser.loadURI(TESTROOT + "unsigned.xpi");
}
function allow_blocked(installInfo) {
ok(true, "Seen blocked");
return false;
}
function finish_test(count) {
is(count, 0, "No add-ons should have been installed");
Services.perms.remove("example.org", "install");
Services.prefs.clearUserPref("xpinstall.whitelist.directRequest");
gBrowser.removeCurrentTab();
Harness.finish();
}