зеркало из https://github.com/mozilla/gecko-dev.git
Backed out 3 changesets (bug 1579489) for causing bc failures at browser_ext_webrtc.js CLOSED TREE
Backed out changeset 71978ebe41f1 (bug 1579489) Backed out changeset b5e35c96c2f7 (bug 1579489) Backed out changeset 71130160afee (bug 1579489)
This commit is contained in:
Родитель
9b17ca23e1
Коммит
ee8e5475f4
|
@ -273,7 +273,6 @@ skip-if = os == 'mac' # Save as PDF not supported on Mac OS X
|
|||
[browser_ext_urlbar_contextual_tip.js]
|
||||
[browser_ext_user_events.js]
|
||||
[browser_ext_webRequest.js]
|
||||
[browser_ext_webrtc.js]
|
||||
[browser_ext_webNavigation_frameId0.js]
|
||||
[browser_ext_webNavigation_getFrames.js]
|
||||
[browser_ext_webNavigation_onCreatedNavigationTarget.js]
|
||||
|
|
|
@ -1,125 +0,0 @@
|
|||
"use strict";
|
||||
|
||||
const { PermissionTestUtils } = ChromeUtils.import(
|
||||
"resource://testing-common/PermissionTestUtils.jsm"
|
||||
);
|
||||
|
||||
add_task(async function test_background_request() {
|
||||
let extension = ExtensionTestUtils.loadExtension({
|
||||
manifest: {},
|
||||
async background() {
|
||||
browser.test.onMessage.addListener(async msg => {
|
||||
if (msg.type != "testGUM") {
|
||||
browser.test.fail("unknown message");
|
||||
}
|
||||
|
||||
await browser.test.assertRejects(
|
||||
navigator.mediaDevices.getUserMedia({ audio: true }),
|
||||
/The request is not allowed/,
|
||||
"Calling gUM in background pages throws an error"
|
||||
);
|
||||
browser.test.notifyPass("done");
|
||||
});
|
||||
},
|
||||
});
|
||||
|
||||
await extension.startup();
|
||||
|
||||
let policy = WebExtensionPolicy.getByID(extension.id);
|
||||
let principal = policy.extension.principal;
|
||||
// Add a permission for the extension to make sure that we throw even
|
||||
// if permission was given.
|
||||
PermissionTestUtils.add(principal, "microphone", Services.perms.ALLOW_ACTION);
|
||||
|
||||
let finished = extension.awaitFinish("done");
|
||||
extension.sendMessage({ type: "testGUM" });
|
||||
await finished;
|
||||
|
||||
PermissionTestUtils.remove(principal, "microphone");
|
||||
await extension.unload();
|
||||
});
|
||||
|
||||
let scriptPage = url =>
|
||||
`<html><head><meta charset="utf-8"><script src="${url}"></script></head><body>${url}</body></html>`;
|
||||
|
||||
add_task(async function test_popup_request() {
|
||||
let extension = ExtensionTestUtils.loadExtension({
|
||||
manifest: {
|
||||
browser_action: {
|
||||
default_popup: "popup.html",
|
||||
browser_style: true,
|
||||
},
|
||||
},
|
||||
|
||||
files: {
|
||||
"popup.html": scriptPage("popup.js"),
|
||||
"popup.js": function() {
|
||||
browser.test
|
||||
.assertRejects(
|
||||
navigator.mediaDevices.getUserMedia({ audio: true }),
|
||||
/The request is not allowed/,
|
||||
"Calling gUM in popup pages without permission throws an error"
|
||||
)
|
||||
.then(function() {
|
||||
browser.test.notifyPass("done");
|
||||
});
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
await extension.startup();
|
||||
clickBrowserAction(extension);
|
||||
await extension.awaitFinish("done");
|
||||
await extension.unload();
|
||||
|
||||
extension = ExtensionTestUtils.loadExtension({
|
||||
manifest: {
|
||||
// Use the same url for background page and browserAction popup,
|
||||
// to double-check that the page url is not being used to decide
|
||||
// if webRTC requests should be allowed or not.
|
||||
background: { page: "page.html" },
|
||||
browser_action: {
|
||||
default_popup: "page.html",
|
||||
browser_style: true,
|
||||
},
|
||||
},
|
||||
|
||||
files: {
|
||||
"page.html": scriptPage("page.js"),
|
||||
"page.js": async function() {
|
||||
const isBackgroundPage =
|
||||
window == (await browser.runtime.getBackgroundPage());
|
||||
|
||||
if (isBackgroundPage) {
|
||||
await browser.test.assertRejects(
|
||||
navigator.mediaDevices.getUserMedia({ audio: true }),
|
||||
/The request is not allowed/,
|
||||
"Calling gUM in background pages throws an error"
|
||||
);
|
||||
} else {
|
||||
try {
|
||||
await navigator.mediaDevices.getUserMedia({ audio: true });
|
||||
browser.test.notifyPass("done");
|
||||
} catch (err) {
|
||||
browser.test.fail(`Failed with error ${err.message}`);
|
||||
browser.test.notifyFail("done");
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
// Add a permission for the extension to make sure that we throw even
|
||||
// if permission was given.
|
||||
await extension.startup();
|
||||
|
||||
let policy = WebExtensionPolicy.getByID(extension.id);
|
||||
let principal = policy.extension.principal;
|
||||
|
||||
PermissionTestUtils.add(principal, "microphone", Services.perms.ALLOW_ACTION);
|
||||
clickBrowserAction(extension);
|
||||
|
||||
await extension.awaitFinish("done");
|
||||
PermissionTestUtils.remove(principal, "microphone");
|
||||
await extension.unload();
|
||||
});
|
|
@ -468,115 +468,6 @@ function stopRecording(aBrowser, aRequest) {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if the principal has sufficient permissions
|
||||
* to fulfill the given request. If the request can be
|
||||
* fulfilled, a message is sent to the child
|
||||
* signaling that WebRTC permissions were given and
|
||||
* this function will return true.
|
||||
*/
|
||||
function checkRequestAllowed(aRequest, aPrincipal, aBrowser) {
|
||||
if (!aRequest.secure) {
|
||||
return false;
|
||||
}
|
||||
|
||||
let { audioDevices, videoDevices, sharingScreen } = aRequest;
|
||||
|
||||
let micAllowed =
|
||||
SitePermissions.getForPrincipal(aPrincipal, "microphone").state ==
|
||||
SitePermissions.ALLOW;
|
||||
let camAllowed =
|
||||
SitePermissions.getForPrincipal(aPrincipal, "camera").state ==
|
||||
SitePermissions.ALLOW;
|
||||
|
||||
let perms = Services.perms;
|
||||
let mediaManagerPerm = perms.testExactPermissionFromPrincipal(
|
||||
aPrincipal,
|
||||
"MediaManagerVideo"
|
||||
);
|
||||
if (mediaManagerPerm) {
|
||||
perms.removeFromPrincipal(aPrincipal, "MediaManagerVideo");
|
||||
}
|
||||
|
||||
// Screen sharing shouldn't follow the camera permissions.
|
||||
if (videoDevices.length && sharingScreen) {
|
||||
camAllowed = false;
|
||||
}
|
||||
if (aRequest.isThirdPartyOrigin) {
|
||||
camAllowed = false;
|
||||
micAllowed = false;
|
||||
}
|
||||
|
||||
let activeCamera;
|
||||
let activeMic;
|
||||
|
||||
// Always prompt for screen sharing
|
||||
if (!sharingScreen) {
|
||||
for (let device of videoDevices) {
|
||||
let set = webrtcUI.activePerms.get(aBrowser.outerWindowID);
|
||||
if (set && set.has(aRequest.windowID + device.mediaSource + device.id)) {
|
||||
activeCamera = device;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
for (let device of audioDevices) {
|
||||
let set = webrtcUI.activePerms.get(aBrowser.outerWindowID);
|
||||
if (set && set.has(aRequest.windowID + device.mediaSource + device.id)) {
|
||||
activeMic = device;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (
|
||||
(!audioDevices.length || micAllowed || activeMic) &&
|
||||
(!videoDevices.length || camAllowed || activeCamera)
|
||||
) {
|
||||
let allowedDevices = [];
|
||||
if (videoDevices.length) {
|
||||
allowedDevices.push((activeCamera || videoDevices[0]).deviceIndex);
|
||||
Services.perms.addFromPrincipal(
|
||||
aPrincipal,
|
||||
"MediaManagerVideo",
|
||||
Services.perms.ALLOW_ACTION,
|
||||
Services.perms.EXPIRE_SESSION
|
||||
);
|
||||
}
|
||||
if (audioDevices.length) {
|
||||
allowedDevices.push((activeMic || audioDevices[0]).deviceIndex);
|
||||
}
|
||||
|
||||
// Remember on which URIs we found persistent permissions so that we
|
||||
// can remove them if the user clicks 'Stop Sharing'. There's no
|
||||
// other way for the stop sharing code to know the hostnames of frames
|
||||
// using devices until bug 1066082 is fixed.
|
||||
let browser = aBrowser;
|
||||
browser._devicePermissionPrincipals =
|
||||
browser._devicePermissionPrincipals || [];
|
||||
browser._devicePermissionPrincipals.push(aPrincipal);
|
||||
|
||||
let camNeeded = !!videoDevices.length;
|
||||
let micNeeded = !!audioDevices.length;
|
||||
checkOSPermission(camNeeded, micNeeded).then(havePermission => {
|
||||
if (havePermission) {
|
||||
let mm = browser.messageManager;
|
||||
mm.sendAsyncMessage("webrtc:Allow", {
|
||||
callID: aRequest.callID,
|
||||
windowID: aRequest.windowID,
|
||||
devices: allowedDevices,
|
||||
});
|
||||
} else {
|
||||
denyRequestNoPermission(browser, aRequest);
|
||||
}
|
||||
});
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
function prompt(aBrowser, aRequest) {
|
||||
let {
|
||||
audioDevices,
|
||||
|
@ -590,39 +481,6 @@ function prompt(aBrowser, aRequest) {
|
|||
aRequest.origin
|
||||
);
|
||||
|
||||
// For add-on principals, we immediately check for permission instead
|
||||
// of waiting for the notification to focus. This allows for supporting
|
||||
// cases such as browserAction popups where no prompt is shown.
|
||||
if (principal.addonPolicy) {
|
||||
let isPopup = false;
|
||||
let isBackground = false;
|
||||
|
||||
for (let view of principal.addonPolicy.extension.views) {
|
||||
if (view.viewType == "popup" && view.xulBrowser == aBrowser) {
|
||||
isPopup = true;
|
||||
}
|
||||
if (view.viewType == "background" && view.xulBrowser == aBrowser) {
|
||||
isBackground = true;
|
||||
}
|
||||
}
|
||||
|
||||
// Recording from background pages is considered too sensitive and will
|
||||
// always be denied.
|
||||
if (isBackground) {
|
||||
denyRequest(aBrowser, aRequest);
|
||||
return;
|
||||
}
|
||||
|
||||
// If the request comes from a popup, we don't want to show the prompt,
|
||||
// but we do want to allow the request if the user previously gave permission.
|
||||
if (isPopup) {
|
||||
if (!checkRequestAllowed(aRequest, principal, aBrowser)) {
|
||||
denyRequest(aBrowser, aRequest);
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// If the user has already denied access once in this tab,
|
||||
// deny again without even showing the notification icon.
|
||||
if (
|
||||
|
@ -760,9 +618,105 @@ function prompt(aBrowser, aRequest) {
|
|||
// it is handled synchronously before we add the notification.
|
||||
// Handling of ALLOW is delayed until the popupshowing event,
|
||||
// to avoid granting permissions automatically to background tabs.
|
||||
if (checkRequestAllowed(aRequest, principal, aBrowser)) {
|
||||
this.remove();
|
||||
return true;
|
||||
if (aRequest.secure) {
|
||||
let micAllowed =
|
||||
SitePermissions.getForPrincipal(principal, "microphone").state ==
|
||||
SitePermissions.ALLOW;
|
||||
let camAllowed =
|
||||
SitePermissions.getForPrincipal(principal, "camera").state ==
|
||||
SitePermissions.ALLOW;
|
||||
|
||||
let perms = Services.perms;
|
||||
let mediaManagerPerm = perms.testExactPermissionFromPrincipal(
|
||||
principal,
|
||||
"MediaManagerVideo"
|
||||
);
|
||||
if (mediaManagerPerm) {
|
||||
perms.removeFromPrincipal(principal, "MediaManagerVideo");
|
||||
}
|
||||
|
||||
// Screen sharing shouldn't follow the camera permissions.
|
||||
if (videoDevices.length && sharingScreen) {
|
||||
camAllowed = false;
|
||||
}
|
||||
if (aRequest.isThirdPartyOrigin) {
|
||||
camAllowed = false;
|
||||
micAllowed = false;
|
||||
}
|
||||
|
||||
let activeCamera;
|
||||
let activeMic;
|
||||
|
||||
// Always prompt for screen sharing
|
||||
if (!sharingScreen) {
|
||||
for (let device of videoDevices) {
|
||||
let set = webrtcUI.activePerms.get(aBrowser.outerWindowID);
|
||||
if (
|
||||
set &&
|
||||
set.has(aRequest.windowID + device.mediaSource + device.id)
|
||||
) {
|
||||
activeCamera = device;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
for (let device of audioDevices) {
|
||||
let set = webrtcUI.activePerms.get(aBrowser.outerWindowID);
|
||||
if (
|
||||
set &&
|
||||
set.has(aRequest.windowID + device.mediaSource + device.id)
|
||||
) {
|
||||
activeMic = device;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (
|
||||
(!audioDevices.length || micAllowed || activeMic) &&
|
||||
(!videoDevices.length || camAllowed || activeCamera)
|
||||
) {
|
||||
let allowedDevices = [];
|
||||
if (videoDevices.length) {
|
||||
allowedDevices.push((activeCamera || videoDevices[0]).deviceIndex);
|
||||
Services.perms.addFromPrincipal(
|
||||
principal,
|
||||
"MediaManagerVideo",
|
||||
Services.perms.ALLOW_ACTION,
|
||||
Services.perms.EXPIRE_SESSION
|
||||
);
|
||||
}
|
||||
if (audioDevices.length) {
|
||||
allowedDevices.push((activeMic || audioDevices[0]).deviceIndex);
|
||||
}
|
||||
|
||||
// Remember on which URIs we found persistent permissions so that we
|
||||
// can remove them if the user clicks 'Stop Sharing'. There's no
|
||||
// other way for the stop sharing code to know the hostnames of frames
|
||||
// using devices until bug 1066082 is fixed.
|
||||
let browser = this.browser;
|
||||
browser._devicePermissionPrincipals =
|
||||
browser._devicePermissionPrincipals || [];
|
||||
browser._devicePermissionPrincipals.push(principal);
|
||||
|
||||
let camNeeded = !!videoDevices.length;
|
||||
let micNeeded = !!audioDevices.length;
|
||||
checkOSPermission(camNeeded, micNeeded).then(havePermission => {
|
||||
if (havePermission) {
|
||||
let mm = browser.messageManager;
|
||||
mm.sendAsyncMessage("webrtc:Allow", {
|
||||
callID: aRequest.callID,
|
||||
windowID: aRequest.windowID,
|
||||
devices: allowedDevices,
|
||||
});
|
||||
} else {
|
||||
denyRequestNoPermission(browser, aRequest);
|
||||
}
|
||||
});
|
||||
|
||||
this.remove();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
function listDevices(menupopup, devices) {
|
||||
|
@ -1128,8 +1082,6 @@ function prompt(aBrowser, aRequest) {
|
|||
devices: allowedDevices,
|
||||
});
|
||||
};
|
||||
|
||||
// If we haven't handled the permission yet, we want to show the doorhanger.
|
||||
return false;
|
||||
},
|
||||
};
|
||||
|
@ -1156,7 +1108,6 @@ function prompt(aBrowser, aRequest) {
|
|||
|
||||
options.checkbox = {
|
||||
label: stringBundle.getString("getUserMedia.remember"),
|
||||
checked: principal.isAddonOrExpandedAddonPrincipal,
|
||||
checkedState: reasonForNoPermanentAllow
|
||||
? {
|
||||
disableMainAction: true,
|
||||
|
|
Загрузка…
Ссылка в новой задаче