зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1172870 - Part 2 - Enable ServiceWorkerClients::OpenWindow on e10s desktop. r=smaug
This commit is contained in:
Родитель
bad419762d
Коммит
8255b13467
|
@ -36,6 +36,7 @@
|
||||||
#include "mozilla/CheckedInt.h"
|
#include "mozilla/CheckedInt.h"
|
||||||
#include "mozilla/DebugOnly.h"
|
#include "mozilla/DebugOnly.h"
|
||||||
#include "mozilla/LoadInfo.h"
|
#include "mozilla/LoadInfo.h"
|
||||||
|
#include "mozilla/dom/ContentChild.h"
|
||||||
#include "mozilla/dom/DocumentFragment.h"
|
#include "mozilla/dom/DocumentFragment.h"
|
||||||
#include "mozilla/dom/DOMTypes.h"
|
#include "mozilla/dom/DOMTypes.h"
|
||||||
#include "mozilla/dom/Element.h"
|
#include "mozilla/dom/Element.h"
|
||||||
|
@ -188,6 +189,7 @@
|
||||||
#include "nsViewManager.h"
|
#include "nsViewManager.h"
|
||||||
#include "nsViewportInfo.h"
|
#include "nsViewportInfo.h"
|
||||||
#include "nsWidgetsCID.h"
|
#include "nsWidgetsCID.h"
|
||||||
|
#include "nsIWindowProvider.h"
|
||||||
#include "nsWrapperCacheInlines.h"
|
#include "nsWrapperCacheInlines.h"
|
||||||
#include "nsXULPopupManager.h"
|
#include "nsXULPopupManager.h"
|
||||||
#include "xpcprivate.h" // nsXPConnect
|
#include "xpcprivate.h" // nsXPConnect
|
||||||
|
@ -5206,6 +5208,14 @@ nsContentUtils::RemoveScriptBlocker()
|
||||||
sBlockedScriptRunners->RemoveElementsAt(originalFirstBlocker, blockersCount);
|
sBlockedScriptRunners->RemoveElementsAt(originalFirstBlocker, blockersCount);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* static */
|
||||||
|
nsIWindowProvider*
|
||||||
|
nsContentUtils::GetWindowProviderForContentProcess()
|
||||||
|
{
|
||||||
|
MOZ_ASSERT(XRE_IsContentProcess());
|
||||||
|
return ContentChild::GetSingleton();
|
||||||
|
}
|
||||||
|
|
||||||
/* static */
|
/* static */
|
||||||
void
|
void
|
||||||
nsContentUtils::WarnScriptWasIgnored(nsIDocument* aDocument)
|
nsContentUtils::WarnScriptWasIgnored(nsIDocument* aDocument)
|
||||||
|
|
|
@ -102,6 +102,7 @@ class nsWrapperCache;
|
||||||
class nsAttrValue;
|
class nsAttrValue;
|
||||||
class nsITransferable;
|
class nsITransferable;
|
||||||
class nsPIWindowRoot;
|
class nsPIWindowRoot;
|
||||||
|
class nsIWindowProvider;
|
||||||
|
|
||||||
struct JSPropertyDescriptor;
|
struct JSPropertyDescriptor;
|
||||||
struct JSRuntime;
|
struct JSRuntime;
|
||||||
|
@ -1640,6 +1641,11 @@ public:
|
||||||
return sScriptBlockerCount == 0;
|
return sScriptBlockerCount == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// XXXcatalinb: workaround for weird include error when trying to reference
|
||||||
|
// ipdl types in WindowWatcher.
|
||||||
|
static nsIWindowProvider*
|
||||||
|
GetWindowProviderForContentProcess();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Call this function if !IsSafeToRunScript() and we fail to run the script
|
* Call this function if !IsSafeToRunScript() and we fail to run the script
|
||||||
* (rather than using AddScriptRunner as we usually do). |aDocument| is
|
* (rather than using AddScriptRunner as we usually do). |aDocument| is
|
||||||
|
|
|
@ -776,34 +776,47 @@ ContentChild::ProvideWindowCommon(TabChild* aTabOpener,
|
||||||
bool* aWindowIsNew,
|
bool* aWindowIsNew,
|
||||||
nsIDOMWindow** aReturn)
|
nsIDOMWindow** aReturn)
|
||||||
{
|
{
|
||||||
MOZ_ASSERT(aTabOpener);
|
|
||||||
*aReturn = nullptr;
|
*aReturn = nullptr;
|
||||||
|
|
||||||
const TabId openerTabId = aTabOpener->GetTabId();
|
nsAutoPtr<IPCTabContext> ipcContext;
|
||||||
|
TabId openerTabId = TabId(0);
|
||||||
|
|
||||||
|
if (aTabOpener) {
|
||||||
PopupIPCTabContext context;
|
PopupIPCTabContext context;
|
||||||
|
openerTabId = aTabOpener->GetTabId();
|
||||||
context.opener() = openerTabId;
|
context.opener() = openerTabId;
|
||||||
context.isBrowserElement() = aTabOpener->IsBrowserElement();
|
context.isBrowserElement() = aTabOpener->IsBrowserElement();
|
||||||
|
ipcContext = new IPCTabContext(context);
|
||||||
|
} else {
|
||||||
|
// It's possible to not have a TabChild opener in the case
|
||||||
|
// of ServiceWorker::OpenWindow.
|
||||||
|
UnsafeIPCTabContext unsafeTabContext;
|
||||||
|
ipcContext = new IPCTabContext(unsafeTabContext);
|
||||||
|
}
|
||||||
|
|
||||||
IPCTabContext ipcContext(context);
|
MOZ_ASSERT(ipcContext);
|
||||||
|
|
||||||
TabId tabId;
|
TabId tabId;
|
||||||
SendAllocateTabId(openerTabId,
|
SendAllocateTabId(openerTabId,
|
||||||
ipcContext,
|
*ipcContext,
|
||||||
GetID(),
|
GetID(),
|
||||||
&tabId);
|
&tabId);
|
||||||
|
|
||||||
|
TabContext newTabContext = aTabOpener ? *aTabOpener : TabContext();
|
||||||
RefPtr<TabChild> newChild = new TabChild(this, tabId,
|
RefPtr<TabChild> newChild = new TabChild(this, tabId,
|
||||||
*aTabOpener, aChromeFlags);
|
newTabContext, aChromeFlags);
|
||||||
if (NS_FAILED(newChild->Init())) {
|
if (NS_FAILED(newChild->Init())) {
|
||||||
return NS_ERROR_ABORT;
|
return NS_ERROR_ABORT;
|
||||||
}
|
}
|
||||||
|
|
||||||
context.opener() = aTabOpener;
|
if (aTabOpener) {
|
||||||
|
MOZ_ASSERT(ipcContext->type() == IPCTabContext::TPopupIPCTabContext);
|
||||||
|
ipcContext->get_PopupIPCTabContext().opener() = aTabOpener;
|
||||||
|
}
|
||||||
|
|
||||||
unused << SendPBrowserConstructor(
|
unused << SendPBrowserConstructor(
|
||||||
// We release this ref in DeallocPBrowserChild
|
// We release this ref in DeallocPBrowserChild
|
||||||
RefPtr<TabChild>(newChild).forget().take(),
|
RefPtr<TabChild>(newChild).forget().take(),
|
||||||
tabId, IPCTabContext(context), aChromeFlags,
|
tabId, *ipcContext, aChromeFlags,
|
||||||
GetID(), IsForApp(), IsForBrowser());
|
GetID(), IsForApp(), IsForBrowser());
|
||||||
|
|
||||||
nsAutoCString spec;
|
nsAutoCString spec;
|
||||||
|
@ -823,6 +836,8 @@ ContentChild::ProvideWindowCommon(TabChild* aTabOpener,
|
||||||
NS_ConvertUTF8toUTF16(features),
|
NS_ConvertUTF8toUTF16(features),
|
||||||
aWindowIsNew);
|
aWindowIsNew);
|
||||||
} else {
|
} else {
|
||||||
|
nsAutoCString baseURIString;
|
||||||
|
if (aTabOpener) {
|
||||||
nsCOMPtr<nsPIDOMWindow> opener = do_QueryInterface(aParent);
|
nsCOMPtr<nsPIDOMWindow> opener = do_QueryInterface(aParent);
|
||||||
nsCOMPtr<nsIDocument> doc = opener->GetDoc();
|
nsCOMPtr<nsIDocument> doc = opener->GetDoc();
|
||||||
nsCOMPtr<nsIURI> baseURI = doc->GetDocBaseURI();
|
nsCOMPtr<nsIURI> baseURI = doc->GetDocBaseURI();
|
||||||
|
@ -831,8 +846,8 @@ ContentChild::ProvideWindowCommon(TabChild* aTabOpener,
|
||||||
return NS_ERROR_FAILURE;
|
return NS_ERROR_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
nsAutoCString baseURIString;
|
|
||||||
baseURI->GetSpec(baseURIString);
|
baseURI->GetSpec(baseURIString);
|
||||||
|
}
|
||||||
|
|
||||||
nsresult rv;
|
nsresult rv;
|
||||||
if (!SendCreateWindow(aTabOpener, newChild,
|
if (!SendCreateWindow(aTabOpener, newChild,
|
||||||
|
|
|
@ -5405,10 +5405,12 @@ ContentParent::RecvCreateWindow(PBrowserParent* aThisTab,
|
||||||
MOZ_ASSERT(!(aChromeFlags & nsIWebBrowserChrome::CHROME_PRIVATE_LIFETIME));
|
MOZ_ASSERT(!(aChromeFlags & nsIWebBrowserChrome::CHROME_PRIVATE_LIFETIME));
|
||||||
MOZ_ASSERT(!(aChromeFlags & nsIWebBrowserChrome::CHROME_REMOTE_WINDOW));
|
MOZ_ASSERT(!(aChromeFlags & nsIWebBrowserChrome::CHROME_REMOTE_WINDOW));
|
||||||
|
|
||||||
TabParent* thisTabParent = TabParent::GetFrom(aThisTab);
|
TabParent* thisTabParent = nullptr;
|
||||||
MOZ_ASSERT(thisTabParent);
|
if (aThisTab) {
|
||||||
|
thisTabParent = TabParent::GetFrom(aThisTab);
|
||||||
|
}
|
||||||
|
|
||||||
if (NS_WARN_IF(thisTabParent->IsBrowserOrApp())) {
|
if (NS_WARN_IF(thisTabParent && thisTabParent->IsBrowserOrApp())) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5426,7 +5428,10 @@ ContentParent::RecvCreateWindow(PBrowserParent* aThisTab,
|
||||||
// we must have an opener.
|
// we must have an opener.
|
||||||
newTab->SetHasContentOpener(true);
|
newTab->SetHasContentOpener(true);
|
||||||
|
|
||||||
nsCOMPtr<nsIContent> frame(do_QueryInterface(thisTabParent->GetOwnerElement()));
|
nsCOMPtr<nsIContent> frame;
|
||||||
|
if (thisTabParent) {
|
||||||
|
frame = do_QueryInterface(thisTabParent->GetOwnerElement());
|
||||||
|
}
|
||||||
|
|
||||||
nsCOMPtr<nsPIDOMWindow> parent;
|
nsCOMPtr<nsPIDOMWindow> parent;
|
||||||
if (frame) {
|
if (frame) {
|
||||||
|
@ -5439,7 +5444,10 @@ ContentParent::RecvCreateWindow(PBrowserParent* aThisTab,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
nsCOMPtr<nsIBrowserDOMWindow> browserDOMWin = thisTabParent->GetBrowserDOMWindow();
|
nsCOMPtr<nsIBrowserDOMWindow> browserDOMWin;
|
||||||
|
if (thisTabParent) {
|
||||||
|
browserDOMWin = thisTabParent->GetBrowserDOMWindow();
|
||||||
|
}
|
||||||
|
|
||||||
// If we haven't found a chrome window to open in, just use the most recently
|
// If we haven't found a chrome window to open in, just use the most recently
|
||||||
// opened one.
|
// opened one.
|
||||||
|
@ -5471,8 +5479,10 @@ ContentParent::RecvCreateWindow(PBrowserParent* aThisTab,
|
||||||
}
|
}
|
||||||
|
|
||||||
bool isPrivate = false;
|
bool isPrivate = false;
|
||||||
|
if (thisTabParent) {
|
||||||
nsCOMPtr<nsILoadContext> loadContext = thisTabParent->GetLoadContext();
|
nsCOMPtr<nsILoadContext> loadContext = thisTabParent->GetLoadContext();
|
||||||
loadContext->GetUsePrivateBrowsing(&isPrivate);
|
loadContext->GetUsePrivateBrowsing(&isPrivate);
|
||||||
|
}
|
||||||
|
|
||||||
nsCOMPtr<nsIOpenURIInFrameParams> params = new nsOpenURIInFrameParams();
|
nsCOMPtr<nsIOpenURIInFrameParams> params = new nsOpenURIInFrameParams();
|
||||||
params->SetReferrer(aBaseURI);
|
params->SetReferrer(aBaseURI);
|
||||||
|
|
|
@ -150,10 +150,9 @@ ContentProcessManager::AllocateTabId(const TabId& aOpenerTabId,
|
||||||
|
|
||||||
struct RemoteFrameInfo info;
|
struct RemoteFrameInfo info;
|
||||||
|
|
||||||
const IPCTabContextUnion& contextUnion = aContext.contextUnion();
|
|
||||||
// If it's a PopupIPCTabContext, it's the case that a TabChild want to
|
// If it's a PopupIPCTabContext, it's the case that a TabChild want to
|
||||||
// open a new tab. aOpenerTabId has to be it's parent frame's opener id.
|
// open a new tab. aOpenerTabId has to be it's parent frame's opener id.
|
||||||
if (contextUnion.type() == IPCTabContextUnion::TPopupIPCTabContext) {
|
if (aContext.type() == IPCTabContext::TPopupIPCTabContext) {
|
||||||
auto remoteFrameIter = iter->second.mRemoteFrames.find(aOpenerTabId);
|
auto remoteFrameIter = iter->second.mRemoteFrames.find(aOpenerTabId);
|
||||||
if (remoteFrameIter == iter->second.mRemoteFrames.end()) {
|
if (remoteFrameIter == iter->second.mRemoteFrames.end()) {
|
||||||
ASSERT_UNLESS_FUZZING("Failed to find parent frame's opener id.");
|
ASSERT_UNLESS_FUZZING("Failed to find parent frame's opener id.");
|
||||||
|
@ -162,7 +161,7 @@ ContentProcessManager::AllocateTabId(const TabId& aOpenerTabId,
|
||||||
|
|
||||||
info.mOpenerTabId = remoteFrameIter->second.mOpenerTabId;
|
info.mOpenerTabId = remoteFrameIter->second.mOpenerTabId;
|
||||||
|
|
||||||
const PopupIPCTabContext &ipcContext = contextUnion.get_PopupIPCTabContext();
|
const PopupIPCTabContext &ipcContext = aContext.get_PopupIPCTabContext();
|
||||||
MOZ_ASSERT(ipcContext.opener().type() == PBrowserOrId::TTabId);
|
MOZ_ASSERT(ipcContext.opener().type() == PBrowserOrId::TTabId);
|
||||||
|
|
||||||
remoteFrameIter = iter->second.mRemoteFrames.find(ipcContext.opener().get_TabId());
|
remoteFrameIter = iter->second.mRemoteFrames.find(ipcContext.opener().get_TabId());
|
||||||
|
|
|
@ -1118,7 +1118,7 @@ parent:
|
||||||
sync GetGraphicsDeviceInitData()
|
sync GetGraphicsDeviceInitData()
|
||||||
returns (DeviceInitData aData);
|
returns (DeviceInitData aData);
|
||||||
|
|
||||||
sync CreateWindow(PBrowser aThisTab,
|
sync CreateWindow(nullable PBrowser aThisTab,
|
||||||
PBrowser aNewTab,
|
PBrowser aNewTab,
|
||||||
uint32_t aChromeFlags,
|
uint32_t aChromeFlags,
|
||||||
bool aCalledFromJS,
|
bool aCalledFromJS,
|
||||||
|
|
|
@ -44,22 +44,25 @@ struct FrameIPCTabContext
|
||||||
nsCString signedPkgOriginNoSuffix;
|
nsCString signedPkgOriginNoSuffix;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// XXXcatalinb: This is only used by ServiceWorkerClients::OpenWindow.
|
||||||
|
// Because service workers don't have an associated TabChild
|
||||||
|
// we can't satisfy the security constraints on b2g. As such, the parent
|
||||||
|
// process will accept this tab context only on desktop.
|
||||||
|
struct UnsafeIPCTabContext
|
||||||
|
{ };
|
||||||
|
|
||||||
// IPCTabContext is an analog to mozilla::dom::TabContext. Both specify an
|
// IPCTabContext is an analog to mozilla::dom::TabContext. Both specify an
|
||||||
// iframe/PBrowser's own and containing app-ids and tell you whether the
|
// iframe/PBrowser's own and containing app-ids and tell you whether the
|
||||||
// iframe/PBrowser is a browser frame. But only IPCTabContext is allowed to
|
// iframe/PBrowser is a browser frame. But only IPCTabContext is allowed to
|
||||||
// travel over IPC.
|
// travel over IPC.
|
||||||
//
|
//
|
||||||
// We need IPCTabContext (specifically, PopupIPCTabContext) to prevent a
|
// We need IPCTabContext (specifically, PopupIPCTabContext) to prevent a
|
||||||
// privilege escalation attack by a compromised child process. See the comment
|
// privilege escalation attack by a compromised child process.
|
||||||
// on AllocPBrowser for details.
|
union IPCTabContext
|
||||||
union IPCTabContextUnion
|
|
||||||
{
|
{
|
||||||
PopupIPCTabContext;
|
PopupIPCTabContext;
|
||||||
FrameIPCTabContext;
|
FrameIPCTabContext;
|
||||||
};
|
UnsafeIPCTabContext;
|
||||||
|
|
||||||
struct IPCTabContext {
|
|
||||||
IPCTabContextUnion contextUnion;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -232,10 +232,9 @@ MaybeInvalidTabContext::MaybeInvalidTabContext(const IPCTabContext& aParams)
|
||||||
nsAutoCString originSuffix;
|
nsAutoCString originSuffix;
|
||||||
nsAutoCString signedPkgOriginNoSuffix;
|
nsAutoCString signedPkgOriginNoSuffix;
|
||||||
|
|
||||||
const IPCTabContextUnion& contextUnion = aParams.contextUnion();
|
switch(aParams.type()) {
|
||||||
switch(contextUnion.type()) {
|
case IPCTabContext::TPopupIPCTabContext: {
|
||||||
case IPCTabContextUnion::TPopupIPCTabContext: {
|
const PopupIPCTabContext &ipcContext = aParams.get_PopupIPCTabContext();
|
||||||
const PopupIPCTabContext &ipcContext = contextUnion.get_PopupIPCTabContext();
|
|
||||||
|
|
||||||
TabContext *context;
|
TabContext *context;
|
||||||
if (ipcContext.opener().type() == PBrowserOrId::TPBrowserParent) {
|
if (ipcContext.opener().type() == PBrowserOrId::TPBrowserParent) {
|
||||||
|
@ -281,9 +280,9 @@ MaybeInvalidTabContext::MaybeInvalidTabContext(const IPCTabContext& aParams)
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case IPCTabContextUnion::TFrameIPCTabContext: {
|
case IPCTabContext::TFrameIPCTabContext: {
|
||||||
const FrameIPCTabContext &ipcContext =
|
const FrameIPCTabContext &ipcContext =
|
||||||
contextUnion.get_FrameIPCTabContext();
|
aParams.get_FrameIPCTabContext();
|
||||||
|
|
||||||
containingAppId = ipcContext.frameOwnerAppId();
|
containingAppId = ipcContext.frameOwnerAppId();
|
||||||
signedPkgOriginNoSuffix = ipcContext.signedPkgOriginNoSuffix();
|
signedPkgOriginNoSuffix = ipcContext.signedPkgOriginNoSuffix();
|
||||||
|
@ -291,6 +290,23 @@ MaybeInvalidTabContext::MaybeInvalidTabContext(const IPCTabContext& aParams)
|
||||||
originAttributes.PopulateFromSuffix(originSuffix);
|
originAttributes.PopulateFromSuffix(originSuffix);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case IPCTabContext::TUnsafeIPCTabContext: {
|
||||||
|
// XXXcatalinb: This used *only* by ServiceWorkerClients::OpenWindow.
|
||||||
|
// It is meant as a temporary solution until service workers can
|
||||||
|
// provide a TabChild equivalent. Don't allow this on b2g since
|
||||||
|
// it might be used to escalate privileges.
|
||||||
|
#ifdef MOZ_B2G
|
||||||
|
mInvalidReason = "ServiceWorkerClients::OpenWindow is not supported.";
|
||||||
|
return;
|
||||||
|
#endif
|
||||||
|
if (!Preferences::GetBool("dom.serviceWorkers.enabled", false)) {
|
||||||
|
mInvalidReason = "ServiceWorkers should be enabled.";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
containingAppId = NO_APP_ID;
|
||||||
|
break;
|
||||||
|
}
|
||||||
default: {
|
default: {
|
||||||
MOZ_CRASH();
|
MOZ_CRASH();
|
||||||
}
|
}
|
||||||
|
|
|
@ -71,18 +71,18 @@ nsIContentParent::DeallocPJavaScriptParent(PJavaScriptParent* aParent)
|
||||||
bool
|
bool
|
||||||
nsIContentParent::CanOpenBrowser(const IPCTabContext& aContext)
|
nsIContentParent::CanOpenBrowser(const IPCTabContext& aContext)
|
||||||
{
|
{
|
||||||
const IPCTabContextUnion& contextUnion = aContext.contextUnion();
|
|
||||||
|
|
||||||
// We don't trust the IPCTabContext we receive from the child, so we'll bail
|
|
||||||
// if we receive an IPCTabContext that's not a PopupIPCTabContext.
|
|
||||||
// (PopupIPCTabContext lets the child process prove that it has access to
|
// (PopupIPCTabContext lets the child process prove that it has access to
|
||||||
// the app it's trying to open.)
|
// the app it's trying to open.)
|
||||||
if (contextUnion.type() != IPCTabContextUnion::TPopupIPCTabContext) {
|
// On e10s we also allow UnsafeTabContext to allow service workers to open
|
||||||
|
// windows. This is enforced in MaybeInvalidTabContext.
|
||||||
|
if (aContext.type() != IPCTabContext::TPopupIPCTabContext &&
|
||||||
|
aContext.type() != IPCTabContext::TUnsafeIPCTabContext) {
|
||||||
ASSERT_UNLESS_FUZZING("Unexpected IPCTabContext type. Aborting AllocPBrowserParent.");
|
ASSERT_UNLESS_FUZZING("Unexpected IPCTabContext type. Aborting AllocPBrowserParent.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
const PopupIPCTabContext& popupContext = contextUnion.get_PopupIPCTabContext();
|
if (aContext.type() == IPCTabContext::TPopupIPCTabContext) {
|
||||||
|
const PopupIPCTabContext& popupContext = aContext.get_PopupIPCTabContext();
|
||||||
if (popupContext.opener().type() != PBrowserOrId::TPBrowserParent) {
|
if (popupContext.opener().type() != PBrowserOrId::TPBrowserParent) {
|
||||||
ASSERT_UNLESS_FUZZING("Unexpected PopupIPCTabContext type. Aborting AllocPBrowserParent.");
|
ASSERT_UNLESS_FUZZING("Unexpected PopupIPCTabContext type. Aborting AllocPBrowserParent.");
|
||||||
return false;
|
return false;
|
||||||
|
@ -101,6 +101,7 @@ nsIContentParent::CanOpenBrowser(const IPCTabContext& aContext)
|
||||||
ASSERT_UNLESS_FUZZING("Child trying to escalate privileges! Aborting AllocPBrowserParent.");
|
ASSERT_UNLESS_FUZZING("Child trying to escalate privileges! Aborting AllocPBrowserParent.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
MaybeInvalidTabContext tc(aContext);
|
MaybeInvalidTabContext tc(aContext);
|
||||||
if (!tc.IsValid()) {
|
if (!tc.IsValid()) {
|
||||||
|
@ -129,14 +130,12 @@ nsIContentParent::AllocPBrowserParent(const TabId& aTabId,
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
const IPCTabContextUnion& contextUnion = aContext.contextUnion();
|
|
||||||
const PopupIPCTabContext& popupContext = contextUnion.get_PopupIPCTabContext();
|
|
||||||
|
|
||||||
uint32_t chromeFlags = aChromeFlags;
|
uint32_t chromeFlags = aChromeFlags;
|
||||||
|
if (aContext.type() == IPCTabContext::TPopupIPCTabContext) {
|
||||||
// CanOpenBrowser has ensured that the IPCTabContext is of
|
// CanOpenBrowser has ensured that the IPCTabContext is of
|
||||||
// type PopupIPCTabContext, and that the opener TabParent is
|
// type PopupIPCTabContext, and that the opener TabParent is
|
||||||
// reachable.
|
// reachable.
|
||||||
|
const PopupIPCTabContext& popupContext = aContext.get_PopupIPCTabContext();
|
||||||
auto opener = TabParent::GetFrom(popupContext.opener().get_PBrowserParent());
|
auto opener = TabParent::GetFrom(popupContext.opener().get_PBrowserParent());
|
||||||
// We must ensure that the private browsing and remoteness flags
|
// We must ensure that the private browsing and remoteness flags
|
||||||
// match those of the opener.
|
// match those of the opener.
|
||||||
|
@ -150,6 +149,7 @@ nsIContentParent::AllocPBrowserParent(const TabId& aTabId,
|
||||||
if (isPrivate) {
|
if (isPrivate) {
|
||||||
chromeFlags |= nsIWebBrowserChrome::CHROME_PRIVATE_WINDOW;
|
chromeFlags |= nsIWebBrowserChrome::CHROME_PRIVATE_WINDOW;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// And because we're allocating a remote browser, of course the
|
// And because we're allocating a remote browser, of course the
|
||||||
// window is remote.
|
// window is remote.
|
||||||
|
|
|
@ -20,9 +20,12 @@
|
||||||
#include "nsIDOMChromeWindow.h"
|
#include "nsIDOMChromeWindow.h"
|
||||||
#include "nsIDOMWindow.h"
|
#include "nsIDOMWindow.h"
|
||||||
#include "nsIWebNavigation.h"
|
#include "nsIWebNavigation.h"
|
||||||
#include "nsIWindowMediator.h"
|
|
||||||
#include "nsIWebProgress.h"
|
#include "nsIWebProgress.h"
|
||||||
#include "nsIWebProgressListener.h"
|
#include "nsIWebProgressListener.h"
|
||||||
|
#include "nsIWindowMediator.h"
|
||||||
|
#include "nsIWindowWatcher.h"
|
||||||
|
#include "nsPIWindowWatcher.h"
|
||||||
|
#include "nsWindowWatcher.h"
|
||||||
#include "nsWeakReference.h"
|
#include "nsWeakReference.h"
|
||||||
|
|
||||||
using namespace mozilla;
|
using namespace mozilla;
|
||||||
|
@ -498,6 +501,31 @@ private:
|
||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (XRE_IsContentProcess()) {
|
||||||
|
// ContentProcess
|
||||||
|
nsCOMPtr<nsIWindowWatcher> wwatch =
|
||||||
|
do_GetService(NS_WINDOWWATCHER_CONTRACTID, &rv);
|
||||||
|
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||||
|
return rv;
|
||||||
|
}
|
||||||
|
nsCOMPtr<nsPIWindowWatcher> pwwatch(do_QueryInterface(wwatch));
|
||||||
|
NS_ENSURE_STATE(pwwatch);
|
||||||
|
|
||||||
|
nsCString spec;
|
||||||
|
uri->GetSpec(spec);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIDOMWindow> newWindow;
|
||||||
|
pwwatch->OpenWindow2(nullptr,
|
||||||
|
spec.get(),
|
||||||
|
nullptr,
|
||||||
|
nullptr,
|
||||||
|
false, false, true, nullptr, nullptr,
|
||||||
|
getter_AddRefs(newWindow));
|
||||||
|
nsCOMPtr<nsPIDOMWindow> pwindow = do_QueryInterface(newWindow);
|
||||||
|
pwindow.forget(aWindow);
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
// Find the most recent browser window and open a new tab in it.
|
// Find the most recent browser window and open a new tab in it.
|
||||||
nsCOMPtr<nsIDOMWindow> browserWindow;
|
nsCOMPtr<nsIDOMWindow> browserWindow;
|
||||||
rv = wm->GetMostRecentWindow(MOZ_UTF16("navigator:browser"),
|
rv = wm->GetMostRecentWindow(MOZ_UTF16("navigator:browser"),
|
||||||
|
@ -580,13 +608,6 @@ already_AddRefed<Promise>
|
||||||
ServiceWorkerClients::OpenWindow(const nsAString& aUrl,
|
ServiceWorkerClients::OpenWindow(const nsAString& aUrl,
|
||||||
ErrorResult& aRv)
|
ErrorResult& aRv)
|
||||||
{
|
{
|
||||||
// XXXcatalinb: This works only on non-multiprocess for now, bail if we're
|
|
||||||
// running in a content process.
|
|
||||||
if (XRE_IsContentProcess()) {
|
|
||||||
aRv.Throw(NS_ERROR_DOM_NOT_SUPPORTED_ERR);
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
WorkerPrivate* workerPrivate = GetCurrentThreadWorkerPrivate();
|
WorkerPrivate* workerPrivate = GetCurrentThreadWorkerPrivate();
|
||||||
MOZ_ASSERT(workerPrivate);
|
MOZ_ASSERT(workerPrivate);
|
||||||
|
|
||||||
|
|
|
@ -545,8 +545,8 @@ nsWindowWatcher::OpenWindowInternal(nsIDOMWindow* aParent,
|
||||||
|
|
||||||
// no extant window? make a new one.
|
// no extant window? make a new one.
|
||||||
|
|
||||||
// If no parent, consider it chrome.
|
// If no parent, consider it chrome when running in the parent process.
|
||||||
bool hasChromeParent = true;
|
bool hasChromeParent = XRE_IsContentProcess() ? false : true;
|
||||||
if (aParent) {
|
if (aParent) {
|
||||||
// Check if the parent document has chrome privileges.
|
// Check if the parent document has chrome privileges.
|
||||||
nsIDocument* doc = parentWindow->GetDoc();
|
nsIDocument* doc = parentWindow->GetDoc();
|
||||||
|
@ -613,7 +613,9 @@ nsWindowWatcher::OpenWindowInternal(nsIDOMWindow* aParent,
|
||||||
// based on whether the docshell type is chrome or content.
|
// based on whether the docshell type is chrome or content.
|
||||||
|
|
||||||
nsCOMPtr<nsIGlobalObject> parentGlobalObject = do_QueryInterface(aParent);
|
nsCOMPtr<nsIGlobalObject> parentGlobalObject = do_QueryInterface(aParent);
|
||||||
if (NS_WARN_IF(!jsapiChromeGuard.Init(parentGlobalObject))) {
|
if (!aParent) {
|
||||||
|
jsapiChromeGuard.Init();
|
||||||
|
} else if (NS_WARN_IF(!jsapiChromeGuard.Init(parentGlobalObject))) {
|
||||||
return NS_ERROR_UNEXPECTED;
|
return NS_ERROR_UNEXPECTED;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -645,10 +647,16 @@ nsWindowWatcher::OpenWindowInternal(nsIDOMWindow* aParent,
|
||||||
!(chromeFlags & (nsIWebBrowserChrome::CHROME_MODAL |
|
!(chromeFlags & (nsIWebBrowserChrome::CHROME_MODAL |
|
||||||
nsIWebBrowserChrome::CHROME_OPENAS_DIALOG |
|
nsIWebBrowserChrome::CHROME_OPENAS_DIALOG |
|
||||||
nsIWebBrowserChrome::CHROME_OPENAS_CHROME))) {
|
nsIWebBrowserChrome::CHROME_OPENAS_CHROME))) {
|
||||||
nsCOMPtr<nsIWindowProvider> provider = do_GetInterface(parentTreeOwner);
|
nsCOMPtr<nsIWindowProvider> provider;
|
||||||
if (provider) {
|
if (parentTreeOwner) {
|
||||||
NS_ASSERTION(aParent, "We've _got_ to have a parent here!");
|
provider = do_GetInterface(parentTreeOwner);
|
||||||
|
} else if (XRE_IsContentProcess()) {
|
||||||
|
// we're in a content process but we don't have a tabchild we can
|
||||||
|
// use.
|
||||||
|
provider = nsContentUtils::GetWindowProviderForContentProcess();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (provider) {
|
||||||
nsCOMPtr<nsIDOMWindow> newWindow;
|
nsCOMPtr<nsIDOMWindow> newWindow;
|
||||||
rv = provider->ProvideWindow(aParent, chromeFlags, aCalledFromJS,
|
rv = provider->ProvideWindow(aParent, chromeFlags, aCalledFromJS,
|
||||||
sizeSpec.PositionSpecified(),
|
sizeSpec.PositionSpecified(),
|
||||||
|
|
Загрузка…
Ссылка в новой задаче