зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1616353 - Part 10.1: Remove special handling of window.open in mozbrowser, r=kmag
There are no remaining users of mozbrowser in our tree, so this patch removes the logic which used to exist for handling window.open differently within mozbrowser frames. Differential Revision: https://phabricator.services.mozilla.com/D67057 --HG-- extra : moz-landing-system : lando
This commit is contained in:
Родитель
0ae579a95d
Коммит
f2bae1efc6
|
@ -1,275 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "BrowserParent.h"
|
||||
|
||||
// BrowserParent.h transitively includes <windows.h>, which does
|
||||
// #define CreateEvent CreateEventW
|
||||
// That messes up our call to EventDispatcher::CreateEvent below.
|
||||
|
||||
#ifdef CreateEvent
|
||||
# undef CreateEvent
|
||||
#endif
|
||||
|
||||
#include "BrowserElementParent.h"
|
||||
#include "mozilla/EventDispatcher.h"
|
||||
#include "mozilla/dom/DocumentInlines.h"
|
||||
#include "mozilla/dom/HTMLIFrameElement.h"
|
||||
#include "mozilla/dom/ToJSValue.h"
|
||||
#include "mozilla/dom/WindowProxyHolder.h"
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsVariant.h"
|
||||
#include "mozilla/dom/BrowserElementDictionariesBinding.h"
|
||||
#include "mozilla/dom/CustomEvent.h"
|
||||
|
||||
using namespace mozilla;
|
||||
using namespace mozilla::dom;
|
||||
using namespace mozilla::layers;
|
||||
using namespace mozilla::layout;
|
||||
|
||||
namespace {
|
||||
|
||||
using mozilla::BrowserElementParent;
|
||||
/**
|
||||
* Create an <iframe mozbrowser> owned by the same document as
|
||||
* aOpenerFrameElement.
|
||||
*/
|
||||
already_AddRefed<HTMLIFrameElement> CreateIframe(Element* aOpenerFrameElement,
|
||||
const nsAString& aName,
|
||||
bool aRemote) {
|
||||
nsNodeInfoManager* nodeInfoManager =
|
||||
aOpenerFrameElement->OwnerDoc()->NodeInfoManager();
|
||||
|
||||
RefPtr<NodeInfo> nodeInfo = nodeInfoManager->GetNodeInfo(
|
||||
nsGkAtoms::iframe,
|
||||
/* aPrefix = */ nullptr, kNameSpaceID_XHTML, nsINode::ELEMENT_NODE);
|
||||
|
||||
RefPtr<HTMLIFrameElement> popupFrameElement =
|
||||
static_cast<HTMLIFrameElement*>(NS_NewHTMLIFrameElement(
|
||||
nodeInfo.forget(), mozilla::dom::NOT_FROM_PARSER));
|
||||
|
||||
popupFrameElement->SetMozbrowser(true);
|
||||
|
||||
// Copy the window name onto the iframe.
|
||||
popupFrameElement->SetAttr(kNameSpaceID_None, nsGkAtoms::name, aName,
|
||||
/* aNotify = */ false);
|
||||
|
||||
// Indicate whether the iframe is should be remote.
|
||||
popupFrameElement->SetAttr(
|
||||
kNameSpaceID_None, nsGkAtoms::remote,
|
||||
aRemote ? NS_LITERAL_STRING("true") : NS_LITERAL_STRING("false"),
|
||||
/* aNotify = */ false);
|
||||
|
||||
// Copy the opener frame's mozprivatebrowsing attribute to the popup frame.
|
||||
nsAutoString mozprivatebrowsing;
|
||||
if (aOpenerFrameElement->GetAttr(kNameSpaceID_None,
|
||||
nsGkAtoms::mozprivatebrowsing,
|
||||
mozprivatebrowsing)) {
|
||||
popupFrameElement->SetAttr(kNameSpaceID_None, nsGkAtoms::mozprivatebrowsing,
|
||||
mozprivatebrowsing, /* aNotify = */ false);
|
||||
}
|
||||
|
||||
return popupFrameElement.forget();
|
||||
}
|
||||
|
||||
bool DispatchCustomDOMEvent(Element* aFrameElement, const nsAString& aEventName,
|
||||
JSContext* cx, JS::Handle<JS::Value> aDetailValue,
|
||||
nsEventStatus* aStatus) {
|
||||
NS_ENSURE_TRUE(aFrameElement, false);
|
||||
RefPtr<nsPresContext> presContext =
|
||||
aFrameElement->OwnerDoc()->GetPresContext();
|
||||
|
||||
RefPtr<CustomEvent> event =
|
||||
NS_NewDOMCustomEvent(aFrameElement, presContext, nullptr);
|
||||
|
||||
event->InitCustomEvent(cx, aEventName,
|
||||
/* aCanBubble = */ true,
|
||||
/* aCancelable = */ true, aDetailValue);
|
||||
|
||||
event->SetTrusted(true);
|
||||
// Dispatch the event.
|
||||
// We don't initialize aStatus here, as our callers have already done so.
|
||||
nsresult rv = EventDispatcher::DispatchDOMEvent(aFrameElement, nullptr, event,
|
||||
presContext, aStatus);
|
||||
return NS_SUCCEEDED(rv);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
/**
|
||||
* Dispatch a mozbrowseropenwindow event to the given opener frame element.
|
||||
* The "popup iframe" (event.detail.frameElement) will be |aPopupFrameElement|.
|
||||
*
|
||||
* Returns true iff there were no unexpected failures and the window.open call
|
||||
* was accepted by the embedder.
|
||||
*/
|
||||
/*static*/
|
||||
BrowserElementParent::OpenWindowResult
|
||||
BrowserElementParent::DispatchOpenWindowEvent(Element* aOpenerFrameElement,
|
||||
Element* aPopupFrameElement,
|
||||
const nsAString& aURL,
|
||||
const nsAString& aName,
|
||||
bool aForceNoReferrer,
|
||||
const nsAString& aFeatures) {
|
||||
// Dispatch a CustomEvent at aOpenerFrameElement with a detail object
|
||||
// (OpenWindowEventDetail) containing aPopupFrameElement, aURL, aName, and
|
||||
// aFeatures.
|
||||
|
||||
// Create the event's detail object.
|
||||
OpenWindowEventDetail detail;
|
||||
if (aURL.IsEmpty()) {
|
||||
// URL should never be empty. Assign about:blank as default.
|
||||
detail.mUrl = NS_LITERAL_STRING("about:blank");
|
||||
} else {
|
||||
detail.mUrl = aURL;
|
||||
}
|
||||
detail.mName = aName;
|
||||
detail.mFeatures = aFeatures;
|
||||
detail.mFrameElement = aPopupFrameElement;
|
||||
detail.mForceNoReferrer = aForceNoReferrer;
|
||||
|
||||
nsIGlobalObject* sgo = aPopupFrameElement->OwnerDoc()->GetScopeObject();
|
||||
if (!sgo) {
|
||||
return BrowserElementParent::OPEN_WINDOW_IGNORED;
|
||||
}
|
||||
|
||||
AutoJSAPI jsapi;
|
||||
if (!jsapi.Init(sgo)) {
|
||||
return BrowserElementParent::OPEN_WINDOW_IGNORED;
|
||||
}
|
||||
|
||||
JSContext* cx = jsapi.cx();
|
||||
JS::Rooted<JS::Value> val(cx);
|
||||
|
||||
JS::Rooted<JSObject*> global(cx, sgo->GetGlobalJSObject());
|
||||
JSAutoRealm ar(cx, global);
|
||||
if (!ToJSValue(cx, detail, &val)) {
|
||||
MOZ_CRASH("Failed to convert dictionary to JS::Value due to OOM.");
|
||||
return BrowserElementParent::OPEN_WINDOW_IGNORED;
|
||||
}
|
||||
|
||||
nsEventStatus status = nsEventStatus_eIgnore;
|
||||
bool dispatchSucceeded = DispatchCustomDOMEvent(
|
||||
aOpenerFrameElement, NS_LITERAL_STRING("mozbrowseropenwindow"), cx, val,
|
||||
&status);
|
||||
|
||||
if (dispatchSucceeded) {
|
||||
if (aPopupFrameElement->IsInComposedDoc()) {
|
||||
return BrowserElementParent::OPEN_WINDOW_ADDED;
|
||||
}
|
||||
if (status == nsEventStatus_eConsumeNoDefault) {
|
||||
// If the frame was not added to a document, report to callers whether
|
||||
// preventDefault was called on or not
|
||||
return BrowserElementParent::OPEN_WINDOW_CANCELLED;
|
||||
}
|
||||
}
|
||||
|
||||
return BrowserElementParent::OPEN_WINDOW_IGNORED;
|
||||
}
|
||||
|
||||
/*static*/
|
||||
BrowserElementParent::OpenWindowResult BrowserElementParent::OpenWindowOOP(
|
||||
BrowserParent* aOpenerBrowserParent, BrowserParent* aPopupBrowserParent,
|
||||
const nsAString& aURL, const nsAString& aName, bool aForceNoReferrer,
|
||||
const nsAString& aFeatures) {
|
||||
// Create an iframe owned by the same document which owns openerFrameElement.
|
||||
nsCOMPtr<Element> openerFrameElement =
|
||||
aOpenerBrowserParent->GetOwnerElement();
|
||||
NS_ENSURE_TRUE(openerFrameElement, BrowserElementParent::OPEN_WINDOW_IGNORED);
|
||||
RefPtr<HTMLIFrameElement> popupFrameElement =
|
||||
CreateIframe(openerFrameElement, aName, /* aRemote = */ true);
|
||||
|
||||
// Normally an <iframe> element will try to create a frameLoader when the
|
||||
// page touches iframe.contentWindow or sets iframe.src.
|
||||
//
|
||||
// But in our case, we want to delay the creation of the frameLoader until
|
||||
// we've verified that the popup has gone through successfully. If the popup
|
||||
// is "blocked" by the embedder, we don't want to load the popup's url.
|
||||
//
|
||||
// Therefore we call DisallowCreateFrameLoader() on the element and call
|
||||
// AllowCreateFrameLoader() only after we've verified that the popup was
|
||||
// allowed.
|
||||
popupFrameElement->DisallowCreateFrameLoader();
|
||||
|
||||
OpenWindowResult opened =
|
||||
DispatchOpenWindowEvent(openerFrameElement, popupFrameElement, aURL,
|
||||
aName, aForceNoReferrer, aFeatures);
|
||||
|
||||
if (opened != BrowserElementParent::OPEN_WINDOW_ADDED) {
|
||||
return opened;
|
||||
}
|
||||
|
||||
// The popup was not blocked, so hook up the frame element and the popup tab
|
||||
// parent, and return success.
|
||||
aPopupBrowserParent->SetOwnerElement(popupFrameElement);
|
||||
popupFrameElement->AllowCreateFrameLoader();
|
||||
popupFrameElement->CreateRemoteFrameLoader(aPopupBrowserParent);
|
||||
|
||||
return opened;
|
||||
}
|
||||
|
||||
/* static */
|
||||
BrowserElementParent::OpenWindowResult
|
||||
BrowserElementParent::OpenWindowInProcess(BrowsingContext* aOpenerWindow,
|
||||
nsIURI* aURI, const nsAString& aName,
|
||||
const nsACString& aFeatures,
|
||||
bool aForceNoOpener,
|
||||
BrowsingContext** aReturnBC) {
|
||||
*aReturnBC = nullptr;
|
||||
|
||||
// If we call window.open from an <iframe> inside an <iframe mozbrowser>,
|
||||
// it's as though the top-level document inside the <iframe mozbrowser>
|
||||
// called window.open. (Indeed, in the OOP case, the inner <iframe> lives
|
||||
// out-of-process, so we couldn't touch it if we tried.)
|
||||
//
|
||||
// GetInProcessScriptableTop gets us the <iframe mozbrowser>'s window; we'll
|
||||
// use its frame element, rather than aOpenerWindow's frame element, as our
|
||||
// "opener frame element" below.
|
||||
nsCOMPtr<nsPIDOMWindowOuter> win =
|
||||
aOpenerWindow->GetDOMWindow()->GetInProcessScriptableTop();
|
||||
|
||||
nsCOMPtr<Element> openerFrameElement = win->GetFrameElementInternal();
|
||||
NS_ENSURE_TRUE(openerFrameElement, BrowserElementParent::OPEN_WINDOW_IGNORED);
|
||||
|
||||
RefPtr<HTMLIFrameElement> popupFrameElement =
|
||||
CreateIframe(openerFrameElement, aName, /* aRemote = */ false);
|
||||
NS_ENSURE_TRUE(popupFrameElement, BrowserElementParent::OPEN_WINDOW_IGNORED);
|
||||
|
||||
nsAutoCString spec;
|
||||
if (aURI) {
|
||||
aURI->GetSpec(spec);
|
||||
}
|
||||
|
||||
if (!aForceNoOpener) {
|
||||
ErrorResult res;
|
||||
popupFrameElement->PresetOpenerWindow(WindowProxyHolder(aOpenerWindow),
|
||||
res);
|
||||
MOZ_ASSERT(!res.Failed());
|
||||
}
|
||||
|
||||
OpenWindowResult opened = DispatchOpenWindowEvent(
|
||||
openerFrameElement, popupFrameElement, NS_ConvertUTF8toUTF16(spec), aName,
|
||||
false, NS_ConvertUTF8toUTF16(aFeatures));
|
||||
|
||||
if (opened != BrowserElementParent::OPEN_WINDOW_ADDED) {
|
||||
return opened;
|
||||
}
|
||||
|
||||
// Return popupFrameElement's window.
|
||||
RefPtr<nsFrameLoader> frameLoader = popupFrameElement->GetFrameLoader();
|
||||
NS_ENSURE_TRUE(frameLoader, BrowserElementParent::OPEN_WINDOW_IGNORED);
|
||||
|
||||
nsCOMPtr<nsIDocShell> docshell = frameLoader->GetDocShell(IgnoreErrors());
|
||||
NS_ENSURE_TRUE(docshell, BrowserElementParent::OPEN_WINDOW_IGNORED);
|
||||
|
||||
docshell->GetBrowsingContextXPCOM(aReturnBC);
|
||||
|
||||
return *aReturnBC ? opened : BrowserElementParent::OPEN_WINDOW_CANCELLED;
|
||||
}
|
||||
|
||||
} // namespace mozilla
|
|
@ -1,121 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef mozilla_BrowserElementHelpers_h
|
||||
#define mozilla_BrowserElementHelpers_h
|
||||
|
||||
#include "nsAString.h"
|
||||
#include "mozilla/gfx/Point.h"
|
||||
#include "mozilla/gfx/Rect.h"
|
||||
#include "Units.h"
|
||||
#include "mozilla/dom/Element.h"
|
||||
|
||||
class nsIDOMWindow;
|
||||
class nsIURI;
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
namespace dom {
|
||||
class BrowsingContext;
|
||||
class BrowserParent;
|
||||
} // namespace dom
|
||||
|
||||
/**
|
||||
* BrowserElementParent implements a portion of the parent-process side of
|
||||
* <iframe mozbrowser>.
|
||||
*
|
||||
* Most of the parent-process side of <iframe mozbrowser> is implemented in
|
||||
* BrowserElementParent.js. This file implements the few parts of this
|
||||
* functionality which must be written in C++.
|
||||
*
|
||||
* We don't communicate with the JS code that lives in BrowserElementParent.js;
|
||||
* the JS and C++ parts are completely separate.
|
||||
*/
|
||||
class BrowserElementParent {
|
||||
public:
|
||||
/**
|
||||
* Possible results from a window.open call.
|
||||
* ADDED - The frame was added to a document (i.e. handled by the
|
||||
* embedder).
|
||||
* IGNORED - The frame was not added to a document and the embedder
|
||||
* didn't call preventDefault() to prevent the platform from
|
||||
* handling the call.
|
||||
* CANCELLED - The frame was not added to a document, but the embedder still
|
||||
* called preventDefault() to prevent the platform from handling
|
||||
* the call.
|
||||
*/
|
||||
|
||||
enum OpenWindowResult {
|
||||
OPEN_WINDOW_ADDED,
|
||||
OPEN_WINDOW_IGNORED,
|
||||
OPEN_WINDOW_CANCELLED
|
||||
};
|
||||
|
||||
/**
|
||||
* Handle a window.open call from an out-of-process <iframe mozbrowser>.
|
||||
*
|
||||
* window.open inside <iframe mozbrowser> doesn't actually open a new
|
||||
* top-level window. Instead, the "embedder" (the document which contains
|
||||
* the <iframe mozbrowser> whose content called window.open) gets the
|
||||
* opportunity to place a new <iframe mozbrowser> in the DOM somewhere. This
|
||||
* new "popup" iframe acts as the opened window.
|
||||
*
|
||||
* This method proceeds in three steps.
|
||||
*
|
||||
* 1) We fire a mozbrowseropenwindow CustomEvent on the opener
|
||||
* iframe element. This event's detail is an instance of
|
||||
* OpenWindowEventDetail.
|
||||
*
|
||||
* 2) The embedder (the document which contains the opener iframe) can accept
|
||||
* the window.open request by inserting event.detail.frameElement (an
|
||||
* iframe element) into the DOM somewhere.
|
||||
*
|
||||
* 3) If the embedder accepted the window.open request, we return true and
|
||||
* set aPopupBrowserParent's frame element to event.detail.frameElement.
|
||||
* Otherwise, we return false.
|
||||
*
|
||||
* @param aURL the URL the new window should load. The empty string is
|
||||
* allowed.
|
||||
* @param aOpenerBrowserParent the BrowserParent whose BrowserChild called
|
||||
* window.open.
|
||||
* @param aPopupBrowserParent the BrowserParent inside which the opened window
|
||||
* will live.
|
||||
* @return an OpenWindowresult that describes whether the embedder added the
|
||||
* frame to a document and whether it called preventDefault to prevent
|
||||
* the platform from handling the open request.
|
||||
*/
|
||||
static OpenWindowResult OpenWindowOOP(
|
||||
dom::BrowserParent* aOpenerBrowserParent,
|
||||
dom::BrowserParent* aPopupBrowserParent, const nsAString& aURL,
|
||||
const nsAString& aName, bool aForceNoReferrer,
|
||||
const nsAString& aFeatures);
|
||||
|
||||
/**
|
||||
* Handle a window.open call from an in-process <iframe mozbrowser>.
|
||||
*
|
||||
* (These parameter types are silly, but they match what our caller has in
|
||||
* hand. Feel free to add an override, if they are inconvenient to you.)
|
||||
*
|
||||
* @param aURI the URI the new window should load. May be null.
|
||||
* @return an OpenWindowResult that describes whether the browser added the
|
||||
* frame to a document or whether they called preventDefault to
|
||||
* prevent the platform from handling the open request
|
||||
*/
|
||||
static OpenWindowResult OpenWindowInProcess(
|
||||
mozilla::dom::BrowsingContext* aOpenerWindow, nsIURI* aURI,
|
||||
const nsAString& aName, const nsACString& aFeatures, bool aForceNoOpener,
|
||||
mozilla::dom::BrowsingContext** aReturnBC);
|
||||
|
||||
private:
|
||||
static OpenWindowResult DispatchOpenWindowEvent(
|
||||
dom::Element* aOpenerFrameElement, dom::Element* aPopupFrameElement,
|
||||
const nsAString& aURL, const nsAString& aName, bool aForceNoReferrer,
|
||||
const nsAString& aFeatures);
|
||||
};
|
||||
|
||||
} // namespace mozilla
|
||||
|
||||
#endif
|
|
@ -7,14 +7,6 @@
|
|||
with Files("**"):
|
||||
BUG_COMPONENT = ("Core", "DOM: Core & HTML")
|
||||
|
||||
EXPORTS.mozilla += [
|
||||
'BrowserElementParent.h',
|
||||
]
|
||||
|
||||
SOURCES += [
|
||||
'BrowserElementParent.cpp',
|
||||
]
|
||||
|
||||
XPIDL_SOURCES += [
|
||||
'nsIBrowserElementAPI.idl',
|
||||
]
|
||||
|
|
|
@ -32,7 +32,6 @@
|
|||
#include "ipc/nsGUIEventIPC.h"
|
||||
#include "js/JSON.h"
|
||||
#include "mozilla/AsyncEventDispatcher.h"
|
||||
#include "mozilla/BrowserElementParent.h"
|
||||
#include "mozilla/ClearOnShutdown.h"
|
||||
#include "mozilla/EventForwards.h"
|
||||
#include "mozilla/EventListenerManager.h"
|
||||
|
@ -889,17 +888,6 @@ BrowserChild::ProvideWindow(nsIOpenWindowInfo* aOpenWindowInfo,
|
|||
|
||||
RefPtr<BrowsingContext> parent = aOpenWindowInfo->GetParent();
|
||||
|
||||
// If parent is inside an <iframe mozbrowser> and this isn't a request to
|
||||
// open a modal-type window, we're going to create a new <iframe mozbrowser>
|
||||
// and return its window here.
|
||||
nsCOMPtr<nsIDocShell> docshell = parent->GetDocShell();
|
||||
bool iframeMoz =
|
||||
(docshell && docshell->GetIsInMozBrowser() &&
|
||||
!(aChromeFlags & (nsIWebBrowserChrome::CHROME_MODAL |
|
||||
nsIWebBrowserChrome::CHROME_OPENAS_DIALOG |
|
||||
nsIWebBrowserChrome::CHROME_OPENAS_CHROME)));
|
||||
|
||||
if (!iframeMoz) {
|
||||
int32_t openLocation = nsWindowWatcher::GetWindowOpenLocation(
|
||||
parent->GetDOMWindow(), aChromeFlags, aCalledFromJS, aWidthSpecified);
|
||||
|
||||
|
@ -917,13 +905,12 @@ BrowserChild::ProvideWindow(nsIOpenWindowInfo* aOpenWindowInfo,
|
|||
bc.forget(aReturn);
|
||||
return NS_OK;
|
||||
}
|
||||
}
|
||||
|
||||
// Note that ProvideWindowCommon may return NS_ERROR_ABORT if the
|
||||
// open window call was canceled. It's important that we pass this error
|
||||
// code back to our caller.
|
||||
ContentChild* cc = ContentChild::GetSingleton();
|
||||
return cc->ProvideWindowCommon(this, aOpenWindowInfo, iframeMoz, aChromeFlags,
|
||||
return cc->ProvideWindowCommon(this, aOpenWindowInfo, aChromeFlags,
|
||||
aCalledFromJS, aWidthSpecified, aURI, aName,
|
||||
aFeatures, aForceNoOpener, aForceNoReferrer,
|
||||
aLoadState, aWindowIsNew, aReturn);
|
||||
|
|
|
@ -14,7 +14,6 @@
|
|||
# include "mozilla/a11y/ProxyAccessibleBase.h"
|
||||
# include "nsAccessibilityService.h"
|
||||
#endif
|
||||
#include "mozilla/BrowserElementParent.h"
|
||||
#include "mozilla/dom/CancelContentJSOptionsBinding.h"
|
||||
#include "mozilla/dom/ChromeMessageSender.h"
|
||||
#include "mozilla/dom/ContentParent.h"
|
||||
|
@ -3398,35 +3397,6 @@ void BrowserParent::ApzAwareEventRoutingToChild(
|
|||
}
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult BrowserParent::RecvBrowserFrameOpenWindow(
|
||||
PBrowserParent* aOpener, const nsString& aURL, const nsString& aName,
|
||||
bool aForceNoReferrer, const nsString& aFeatures,
|
||||
BrowserFrameOpenWindowResolver&& aResolve) {
|
||||
CreatedWindowInfo cwi;
|
||||
cwi.rv() = NS_OK;
|
||||
cwi.maxTouchPoints() = 0;
|
||||
|
||||
BrowserElementParent::OpenWindowResult opened =
|
||||
BrowserElementParent::OpenWindowOOP(BrowserParent::GetFrom(aOpener), this,
|
||||
aURL, aName, aForceNoReferrer,
|
||||
aFeatures);
|
||||
cwi.windowOpened() = (opened == BrowserElementParent::OPEN_WINDOW_ADDED);
|
||||
cwi.maxTouchPoints() = GetMaxTouchPoints();
|
||||
|
||||
nsCOMPtr<nsIWidget> widget = GetWidget();
|
||||
if (widget) {
|
||||
cwi.dimensions() = GetDimensionInfo();
|
||||
}
|
||||
|
||||
// Resolve the request with the information we collected.
|
||||
aResolve(cwi);
|
||||
|
||||
if (!cwi.windowOpened()) {
|
||||
Destroy();
|
||||
}
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult BrowserParent::RecvRespondStartSwipeEvent(
|
||||
const uint64_t& aInputBlockId, const bool& aStartSwipe) {
|
||||
if (nsCOMPtr<nsIWidget> widget = GetWidget()) {
|
||||
|
|
|
@ -343,11 +343,6 @@ class BrowserParent final : public PBrowserParent,
|
|||
const bool aNeedCollectSHistory, const uint32_t& aFlushId,
|
||||
const bool& aIsFinal, const uint32_t& aEpoch);
|
||||
|
||||
mozilla::ipc::IPCResult RecvBrowserFrameOpenWindow(
|
||||
PBrowserParent* aOpener, const nsString& aURL, const nsString& aName,
|
||||
bool aForceNoReferrer, const nsString& aFeatures,
|
||||
BrowserFrameOpenWindowResolver&& aResolve);
|
||||
|
||||
mozilla::ipc::IPCResult RecvSyncMessage(
|
||||
const nsString& aMessage, const ClonedMessageData& aData,
|
||||
nsTArray<CpowEntry>&& aCpows, nsIPrincipal* aPrincipal,
|
||||
|
|
|
@ -783,7 +783,7 @@ ContentChild::ProvideWindow(nsIOpenWindowInfo* aOpenWindowInfo,
|
|||
bool aForceNoOpener, bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState, bool* aWindowIsNew,
|
||||
BrowsingContext** aReturn) {
|
||||
return ProvideWindowCommon(nullptr, aOpenWindowInfo, false, aChromeFlags,
|
||||
return ProvideWindowCommon(nullptr, aOpenWindowInfo, aChromeFlags,
|
||||
aCalledFromJS, aWidthSpecified, aURI, aName,
|
||||
aFeatures, aForceNoOpener, aForceNoReferrer,
|
||||
aLoadState, aWindowIsNew, aReturn);
|
||||
|
@ -867,11 +867,10 @@ static nsresult GetCreateWindowParams(nsIOpenWindowInfo* aOpenWindowInfo,
|
|||
|
||||
nsresult ContentChild::ProvideWindowCommon(
|
||||
BrowserChild* aTabOpener, nsIOpenWindowInfo* aOpenWindowInfo,
|
||||
bool aIframeMoz, uint32_t aChromeFlags, bool aCalledFromJS,
|
||||
bool aWidthSpecified, nsIURI* aURI, const nsAString& aName,
|
||||
const nsACString& aFeatures, bool aForceNoOpener, bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState, bool* aWindowIsNew,
|
||||
BrowsingContext** aReturn) {
|
||||
uint32_t aChromeFlags, bool aCalledFromJS, bool aWidthSpecified,
|
||||
nsIURI* aURI, const nsAString& aName, const nsACString& aFeatures,
|
||||
bool aForceNoOpener, bool aForceNoReferrer, nsDocShellLoadState* aLoadState,
|
||||
bool* aWindowIsNew, BrowsingContext** aReturn) {
|
||||
*aReturn = nullptr;
|
||||
|
||||
UniquePtr<IPCTabContext> ipcContext;
|
||||
|
@ -1174,24 +1173,6 @@ nsresult ContentChild::ProvideWindowCommon(
|
|||
};
|
||||
|
||||
// Send down the request to open the window.
|
||||
if (aIframeMoz) {
|
||||
MOZ_ASSERT(aTabOpener);
|
||||
nsAutoCString url;
|
||||
if (aURI) {
|
||||
aURI->GetSpec(url);
|
||||
} else {
|
||||
// We can't actually send a nullptr up as the URI, since IPDL doesn't let
|
||||
// us send nullptr's for primitives. We indicate that the nsString for the
|
||||
// URI should be converted to a nullptr by voiding the string.
|
||||
url.SetIsVoid(true);
|
||||
}
|
||||
|
||||
// NOTE: BrowserFrameOpenWindowPromise is the same type as
|
||||
// CreateWindowPromise, and this code depends on that fact.
|
||||
newChild->SendBrowserFrameOpenWindow(
|
||||
aTabOpener, NS_ConvertUTF8toUTF16(url), name, aForceNoReferrer,
|
||||
NS_ConvertUTF8toUTF16(features), std::move(resolve), std::move(reject));
|
||||
} else {
|
||||
float fullZoom;
|
||||
nsCOMPtr<nsIPrincipal> triggeringPrincipal;
|
||||
nsCOMPtr<nsIContentSecurityPolicy> csp;
|
||||
|
@ -1209,17 +1190,14 @@ nsresult ContentChild::ProvideWindowCommon(
|
|||
Principal(triggeringPrincipal), csp, referrerInfo,
|
||||
aOpenWindowInfo->GetOriginAttributes(), std::move(resolve),
|
||||
std::move(reject));
|
||||
}
|
||||
|
||||
// =======================
|
||||
// Begin Nested Event Loop
|
||||
// =======================
|
||||
|
||||
// We have to wait for a response from either SendCreateWindow or
|
||||
// SendBrowserFrameOpenWindow with information we're going to need to return
|
||||
// from this function, So we spin a nested event loop until they get back to
|
||||
// us.
|
||||
//
|
||||
// We have to wait for a response from SendCreateWindow or with information
|
||||
// we're going to need to return from this function, So we spin a nested event
|
||||
// loop until they get back to us.
|
||||
|
||||
// Prevent the docshell from becoming active while the nested event loop is
|
||||
// spinning.
|
||||
|
|
|
@ -111,9 +111,9 @@ class ContentChild final
|
|||
|
||||
nsresult ProvideWindowCommon(BrowserChild* aTabOpener,
|
||||
nsIOpenWindowInfo* aOpenWindowInfo,
|
||||
bool aIframeMoz, uint32_t aChromeFlags,
|
||||
bool aCalledFromJS, bool aWidthSpecified,
|
||||
nsIURI* aURI, const nsAString& aName,
|
||||
uint32_t aChromeFlags, bool aCalledFromJS,
|
||||
bool aWidthSpecified, nsIURI* aURI,
|
||||
const nsAString& aName,
|
||||
const nsACString& aFeatures, bool aForceNoOpener,
|
||||
bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState,
|
||||
|
|
|
@ -484,22 +484,6 @@ parent:
|
|||
*/
|
||||
async IndexedDBPermissionRequest(nsIPrincipal aPrincipal) returns (uint32_t permission);
|
||||
|
||||
/**
|
||||
* window.open from inside <iframe mozbrowser> is special. When the child
|
||||
* process calls window.open, it creates a new PBrowser (in its own
|
||||
* process), then calls BrowserFrameOpenWindow on it.
|
||||
*
|
||||
* The parent process gets a chance to accept or reject the window.open
|
||||
* call, and windowOpened is set to true if we ended up going through with
|
||||
* the window.open.
|
||||
*
|
||||
* @param opener the PBrowser whose content called window.open.
|
||||
*/
|
||||
async BrowserFrameOpenWindow(PBrowser opener,
|
||||
nsString aURL, nsString aName,
|
||||
bool aForceNoReferrer, nsString aFeatures)
|
||||
returns (CreatedWindowInfo window);
|
||||
|
||||
/**
|
||||
* Tells the containing widget whether the given input block results in a
|
||||
* swipe. Should be called in response to a WidgetWheelEvent that has
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include "nsIMIMEInfo.h"
|
||||
#include "nsIWidget.h"
|
||||
#include "nsWindowWatcher.h"
|
||||
#include "mozilla/BrowserElementParent.h"
|
||||
#include "mozilla/Components.h"
|
||||
#include "mozilla/NullPrincipal.h"
|
||||
#include "nsDocShell.h"
|
||||
|
@ -633,50 +632,14 @@ nsContentTreeOwner::ProvideWindow(
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIDocShell> docshell = parent->GetDocShell();
|
||||
#ifdef DEBUG
|
||||
nsCOMPtr<nsIDocShell> docshell = parent->GetDocShell();
|
||||
nsCOMPtr<nsIDocShellTreeOwner> parentOwner = do_GetInterface(docshell);
|
||||
NS_ASSERTION(
|
||||
SameCOMIdentity(parentOwner, static_cast<nsIDocShellTreeOwner*>(this)),
|
||||
"Parent from wrong docshell tree?");
|
||||
#endif
|
||||
|
||||
// If aParent is inside an <iframe mozbrowser> and this isn't a request to
|
||||
// open a modal-type window, we're going to create a new <iframe mozbrowser>
|
||||
// and return its window here.
|
||||
if (docshell && docshell->GetIsInMozBrowser() &&
|
||||
!(aChromeFlags & (nsIWebBrowserChrome::CHROME_MODAL |
|
||||
nsIWebBrowserChrome::CHROME_OPENAS_DIALOG |
|
||||
nsIWebBrowserChrome::CHROME_OPENAS_CHROME))) {
|
||||
BrowserElementParent::OpenWindowResult opened =
|
||||
BrowserElementParent::OpenWindowInProcess(
|
||||
parent, aURI, aName, aFeatures, aForceNoOpener, aReturn);
|
||||
|
||||
// If OpenWindowInProcess handled the open (by opening it or blocking the
|
||||
// popup), tell our caller not to proceed trying to create a new window
|
||||
// through other means.
|
||||
if (opened != BrowserElementParent::OPEN_WINDOW_IGNORED) {
|
||||
*aWindowIsNew = opened == BrowserElementParent::OPEN_WINDOW_ADDED;
|
||||
return *aWindowIsNew ? NS_OK : NS_ERROR_ABORT;
|
||||
}
|
||||
|
||||
// If we're in an app and the target is _blank, send the url to the OS
|
||||
if (aName.LowerCaseEqualsLiteral("_blank")) {
|
||||
nsCOMPtr<nsIExternalURLHandlerService> exUrlServ(
|
||||
do_GetService(NS_EXTERNALURLHANDLERSERVICE_CONTRACTID));
|
||||
if (exUrlServ) {
|
||||
nsCOMPtr<nsIHandlerInfo> info;
|
||||
bool found;
|
||||
exUrlServ->GetURLHandlerInfoFromOS(aURI, &found, getter_AddRefs(info));
|
||||
|
||||
if (info && found) {
|
||||
info->LaunchWithURI(aURI, nullptr);
|
||||
return NS_ERROR_ABORT;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int32_t openLocation = nsWindowWatcher::GetWindowOpenLocation(
|
||||
parent->GetDOMWindow(), aChromeFlags, aCalledFromJS, aWidthSpecified);
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче