зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1561015: Part 1 - Use BrowsingContext in window provider APIs. r=bzbarsky,mossop
This is the first step in making it possible to return remote WindowProxy objects from window.open() and related APIs. This patch also incidentally fixes a bug where getContentWindowOrOpenURI returned the top-level browser window rather than the new content window when passed OPEN_NEWWINDOW for the `aWhere` parameter. This was not the expected behavior, and was a potentially major footgun for any new users who expected to always get the content window for the URL they were loading, rather than sometimes getting a chrome browser window instead. For now, that case just returns null, which is only a minor footgun, rather than the major one we had before. Differential Revision: https://phabricator.services.mozilla.com/D35688 --HG-- extra : moz-landing-system : lando
This commit is contained in:
Родитель
909e9c6f30
Коммит
22592538f5
|
@ -13,6 +13,7 @@
|
|||
#include "imgIContainer.h"
|
||||
#include "imgIRequest.h"
|
||||
#include "nsGenericHTMLElement.h"
|
||||
#include "mozilla/dom/BrowsingContext.h"
|
||||
#include "mozilla/dom/Document.h"
|
||||
#include "nsIImageLoadingContent.h"
|
||||
#include "nsIServiceManager.h"
|
||||
|
@ -109,7 +110,7 @@ bool ImageAccessible::DoAction(uint8_t aIndex) const {
|
|||
nsCOMPtr<nsPIDOMWindowOuter> piWindow = document->GetWindow();
|
||||
if (!piWindow) return false;
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> tmp;
|
||||
RefPtr<mozilla::dom::BrowsingContext> tmp;
|
||||
return NS_SUCCEEDED(piWindow->Open(spec, EmptyString(), EmptyString(),
|
||||
/* aLoadInfo = */ nullptr,
|
||||
/* aForceNoOpener = */ false,
|
||||
|
|
|
@ -6485,7 +6485,7 @@ nsBrowserAccess.prototype = {
|
|||
throw Cr.NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
var newWindow = null;
|
||||
var browsingContext = null;
|
||||
var isExternal = !!(aFlags & Ci.nsIBrowserDOMWindow.OPEN_EXTERNAL);
|
||||
|
||||
if (aOpener && isExternal) {
|
||||
|
@ -6549,7 +6549,7 @@ nsBrowserAccess.prototype = {
|
|||
// Pass all params to openDialog to ensure that "url" isn't passed through
|
||||
// loadOneOrMoreURIs, which splits based on "|"
|
||||
try {
|
||||
newWindow = openDialog(
|
||||
openDialog(
|
||||
AppConstants.BROWSER_CHROME_URL,
|
||||
"_blank",
|
||||
features,
|
||||
|
@ -6566,6 +6566,17 @@ nsBrowserAccess.prototype = {
|
|||
null,
|
||||
aCsp
|
||||
);
|
||||
// At this point, the new browser window is just starting to load, and
|
||||
// hasn't created the content <browser> that we should return. So we
|
||||
// can't actually return a valid BrowsingContext for this load without
|
||||
// spinning the event loop.
|
||||
//
|
||||
// Fortunately, no current callers of this API who pass OPEN_NEWWINDOW
|
||||
// actually use the return value, so we're safe returning null for
|
||||
// now.
|
||||
//
|
||||
// Ideally this should be fixed.
|
||||
browsingContext = null;
|
||||
} catch (ex) {
|
||||
Cu.reportError(ex);
|
||||
}
|
||||
|
@ -6599,12 +6610,13 @@ nsBrowserAccess.prototype = {
|
|||
aCsp
|
||||
);
|
||||
if (browser) {
|
||||
newWindow = browser.contentWindow;
|
||||
browsingContext = browser.browsingContext;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
// OPEN_CURRENTWINDOW or an illegal value
|
||||
newWindow = window.content;
|
||||
browsingContext =
|
||||
window.content && BrowsingContext.getFromWindow(window.content);
|
||||
if (aURI) {
|
||||
let loadflags = isExternal
|
||||
? Ci.nsIWebNavigation.LOAD_FLAGS_FROM_EXTERNAL
|
||||
|
@ -6622,7 +6634,7 @@ nsBrowserAccess.prototype = {
|
|||
window.focus();
|
||||
}
|
||||
}
|
||||
return newWindow;
|
||||
return browsingContext;
|
||||
},
|
||||
|
||||
createContentWindowInFrame: function browser_createContentWindowInFrame(
|
||||
|
|
|
@ -8777,7 +8777,7 @@ nsresult nsDocShell::PerformRetargeting(nsDocShellLoadState* aLoadState,
|
|||
nsCOMPtr<nsPIDOMWindowOuter> win = GetWindow();
|
||||
NS_ENSURE_TRUE(win, NS_ERROR_NOT_AVAILABLE);
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> newWin;
|
||||
RefPtr<BrowsingContext> newBC;
|
||||
nsAutoCString spec;
|
||||
aLoadState->URI()->GetSpec(spec);
|
||||
|
||||
|
@ -8837,20 +8837,21 @@ nsresult nsDocShell::PerformRetargeting(nsDocShellLoadState* aLoadState,
|
|||
EmptyString(), // Features
|
||||
loadState,
|
||||
true, // aForceNoOpener
|
||||
getter_AddRefs(newWin));
|
||||
MOZ_ASSERT(!newWin);
|
||||
getter_AddRefs(newBC));
|
||||
MOZ_ASSERT(!newBC);
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = win->OpenNoNavigate(NS_ConvertUTF8toUTF16(spec),
|
||||
aLoadState->Target(), // window name
|
||||
EmptyString(), // Features
|
||||
getter_AddRefs(newWin));
|
||||
getter_AddRefs(newBC));
|
||||
|
||||
// In some cases the Open call doesn't actually result in a new
|
||||
// window being opened. We can detect these cases by examining the
|
||||
// document in |newWin|, if any.
|
||||
nsCOMPtr<nsPIDOMWindowOuter> piNewWin = newWin;
|
||||
// document in |newBC|, if any.
|
||||
nsCOMPtr<nsPIDOMWindowOuter> piNewWin =
|
||||
newBC ? newBC->GetDOMWindow() : nullptr;
|
||||
if (piNewWin) {
|
||||
RefPtr<Document> newDoc = piNewWin->GetExtantDoc();
|
||||
if (!newDoc || newDoc->IsInitialDocument()) {
|
||||
|
@ -8858,8 +8859,9 @@ nsresult nsDocShell::PerformRetargeting(nsDocShellLoadState* aLoadState,
|
|||
}
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIWebNavigation> webNav = do_GetInterface(newWin);
|
||||
targetDocShell = do_QueryInterface(webNav);
|
||||
if (newBC) {
|
||||
targetDocShell = newBC->GetDocShell();
|
||||
}
|
||||
}
|
||||
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
|
|
@ -8709,12 +8709,12 @@ mozilla::dom::Nullable<mozilla::dom::WindowProxyHolder> Document::Open(
|
|||
return nullptr;
|
||||
}
|
||||
RefPtr<nsGlobalWindowOuter> win = nsGlobalWindowOuter::Cast(outer);
|
||||
nsCOMPtr<nsPIDOMWindowOuter> newWindow;
|
||||
rv = win->OpenJS(aURL, aName, aFeatures, getter_AddRefs(newWindow));
|
||||
if (!newWindow) {
|
||||
RefPtr<BrowsingContext> newBC;
|
||||
rv = win->OpenJS(aURL, aName, aFeatures, getter_AddRefs(newBC));
|
||||
if (!newBC) {
|
||||
return nullptr;
|
||||
}
|
||||
return WindowProxyHolder(newWindow->GetBrowsingContext());
|
||||
return WindowProxyHolder(newBC.forget());
|
||||
}
|
||||
|
||||
Document* Document::Open(const Optional<nsAString>& /* unused */,
|
||||
|
|
|
@ -5734,10 +5734,9 @@ void nsGlobalWindowOuter::FireAbuseEvents(
|
|||
Nullable<WindowProxyHolder> nsGlobalWindowOuter::OpenOuter(
|
||||
const nsAString& aUrl, const nsAString& aName, const nsAString& aOptions,
|
||||
ErrorResult& aError) {
|
||||
nsCOMPtr<nsPIDOMWindowOuter> window;
|
||||
aError = OpenJS(aUrl, aName, aOptions, getter_AddRefs(window));
|
||||
RefPtr<BrowsingContext> bc;
|
||||
if (!window || !(bc = window->GetBrowsingContext())) {
|
||||
aError = OpenJS(aUrl, aName, aOptions, getter_AddRefs(bc));
|
||||
if (!bc) {
|
||||
return nullptr;
|
||||
}
|
||||
return WindowProxyHolder(bc.forget());
|
||||
|
@ -5748,7 +5747,7 @@ nsresult nsGlobalWindowOuter::Open(const nsAString& aUrl,
|
|||
const nsAString& aOptions,
|
||||
nsDocShellLoadState* aLoadState,
|
||||
bool aForceNoOpener,
|
||||
nsPIDOMWindowOuter** _retval) {
|
||||
BrowsingContext** _retval) {
|
||||
return OpenInternal(aUrl, aName, aOptions,
|
||||
false, // aDialog
|
||||
false, // aContentModal
|
||||
|
@ -5762,7 +5761,7 @@ nsresult nsGlobalWindowOuter::Open(const nsAString& aUrl,
|
|||
nsresult nsGlobalWindowOuter::OpenJS(const nsAString& aUrl,
|
||||
const nsAString& aName,
|
||||
const nsAString& aOptions,
|
||||
nsPIDOMWindowOuter** _retval) {
|
||||
BrowsingContext** _retval) {
|
||||
return OpenInternal(aUrl, aName, aOptions,
|
||||
false, // aDialog
|
||||
false, // aContentModal
|
||||
|
@ -5781,7 +5780,7 @@ nsresult nsGlobalWindowOuter::OpenDialog(const nsAString& aUrl,
|
|||
const nsAString& aName,
|
||||
const nsAString& aOptions,
|
||||
nsISupports* aExtraArgument,
|
||||
nsPIDOMWindowOuter** _retval) {
|
||||
BrowsingContext** _retval) {
|
||||
return OpenInternal(aUrl, aName, aOptions,
|
||||
true, // aDialog
|
||||
false, // aContentModal
|
||||
|
@ -5799,7 +5798,7 @@ nsresult nsGlobalWindowOuter::OpenDialog(const nsAString& aUrl,
|
|||
nsresult nsGlobalWindowOuter::OpenNoNavigate(const nsAString& aUrl,
|
||||
const nsAString& aName,
|
||||
const nsAString& aOptions,
|
||||
nsPIDOMWindowOuter** _retval) {
|
||||
BrowsingContext** _retval) {
|
||||
return OpenInternal(aUrl, aName, aOptions,
|
||||
false, // aDialog
|
||||
false, // aContentModal
|
||||
|
@ -5824,7 +5823,7 @@ Nullable<WindowProxyHolder> nsGlobalWindowOuter::OpenDialogOuter(
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> dialog;
|
||||
RefPtr<BrowsingContext> dialog;
|
||||
aError = OpenInternal(aUrl, aName, aOptions,
|
||||
true, // aDialog
|
||||
false, // aContentModal
|
||||
|
@ -5835,11 +5834,10 @@ Nullable<WindowProxyHolder> nsGlobalWindowOuter::OpenDialogOuter(
|
|||
nullptr, // aLoadState
|
||||
false, // aForceNoOpener
|
||||
getter_AddRefs(dialog));
|
||||
RefPtr<BrowsingContext> bc;
|
||||
if (!dialog || !(bc = dialog->GetBrowsingContext())) {
|
||||
if (!dialog) {
|
||||
return nullptr;
|
||||
}
|
||||
return WindowProxyHolder(bc.forget());
|
||||
return WindowProxyHolder(dialog.forget());
|
||||
}
|
||||
|
||||
BrowsingContext* nsGlobalWindowOuter::GetFramesOuter() {
|
||||
|
@ -7131,7 +7129,7 @@ nsresult nsGlobalWindowOuter::OpenInternal(
|
|||
bool aDialog, bool aContentModal, bool aCalledNoScript, bool aDoJSFixups,
|
||||
bool aNavigate, nsIArray* argv, nsISupports* aExtraArgument,
|
||||
nsDocShellLoadState* aLoadState, bool aForceNoOpener,
|
||||
nsPIDOMWindowOuter** aReturn) {
|
||||
BrowsingContext** aReturn) {
|
||||
#ifdef DEBUG
|
||||
uint32_t argc = 0;
|
||||
if (argv) argv->GetLength(&argc);
|
||||
|
@ -7248,7 +7246,7 @@ nsresult nsGlobalWindowOuter::OpenInternal(
|
|||
}
|
||||
}
|
||||
|
||||
nsCOMPtr<mozIDOMWindowProxy> domReturn;
|
||||
RefPtr<BrowsingContext> domReturn;
|
||||
|
||||
nsCOMPtr<nsIWindowWatcher> wwatch =
|
||||
do_GetService(NS_WINDOWWATCHER_CONTRACTID, &rv);
|
||||
|
@ -7277,6 +7275,7 @@ nsresult nsGlobalWindowOuter::OpenInternal(
|
|||
// dialog is open.
|
||||
AutoPopupStatePusher popupStatePusher(PopupBlocker::openAbused, true);
|
||||
|
||||
nsCOMPtr<mozIDOMWindowProxy> win;
|
||||
if (!aCalledNoScript) {
|
||||
// We asserted at the top of this function that aNavigate is true for
|
||||
// !aCalledNoScript.
|
||||
|
@ -7284,7 +7283,7 @@ nsresult nsGlobalWindowOuter::OpenInternal(
|
|||
this, url.IsVoid() ? nullptr : url.get(), name_ptr, options_ptr,
|
||||
/* aCalledFromScript = */ true, aDialog, aNavigate, argv,
|
||||
isPopupSpamWindow, forceNoOpener, forceNoReferrer, aLoadState,
|
||||
getter_AddRefs(domReturn));
|
||||
getter_AddRefs(win));
|
||||
} else {
|
||||
// Force a system caller here so that the window watcher won't screw us
|
||||
// up. We do NOT want this case looking at the JS context on the stack
|
||||
|
@ -7304,7 +7303,10 @@ nsresult nsGlobalWindowOuter::OpenInternal(
|
|||
this, url.IsVoid() ? nullptr : url.get(), name_ptr, options_ptr,
|
||||
/* aCalledFromScript = */ false, aDialog, aNavigate, aExtraArgument,
|
||||
isPopupSpamWindow, forceNoOpener, forceNoReferrer, aLoadState,
|
||||
getter_AddRefs(domReturn));
|
||||
getter_AddRefs(win));
|
||||
}
|
||||
if (win) {
|
||||
domReturn = nsPIDOMWindowOuter::From(win)->GetBrowsingContext();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -7317,7 +7319,8 @@ nsresult nsGlobalWindowOuter::OpenInternal(
|
|||
}
|
||||
|
||||
if (domReturn && aDoJSFixups) {
|
||||
nsCOMPtr<nsIDOMChromeWindow> chrome_win(do_QueryInterface(domReturn));
|
||||
nsCOMPtr<nsIDOMChromeWindow> chrome_win(
|
||||
do_QueryInterface(domReturn->GetDOMWindow()));
|
||||
if (!chrome_win) {
|
||||
// A new non-chrome window was created from a call to
|
||||
// window.open() from JavaScript, make sure there's a document in
|
||||
|
@ -7327,12 +7330,14 @@ nsresult nsGlobalWindowOuter::OpenInternal(
|
|||
// XXXbz should this just use EnsureInnerWindow()?
|
||||
|
||||
// Force document creation.
|
||||
nsCOMPtr<Document> doc = nsPIDOMWindowOuter::From(domReturn)->GetDoc();
|
||||
Unused << doc;
|
||||
if (nsPIDOMWindowOuter* win = domReturn->GetDOMWindow()) {
|
||||
nsCOMPtr<Document> doc = win->GetDoc();
|
||||
Unused << doc;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
*aReturn = do_AddRef(nsPIDOMWindowOuter::From(domReturn)).take();
|
||||
domReturn.forget(aReturn);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
|
|
@ -260,7 +260,8 @@ class nsGlobalWindowOuter final : public mozilla::dom::EventTarget,
|
|||
const nsAString& aGroup);
|
||||
|
||||
nsresult OpenJS(const nsAString& aUrl, const nsAString& aName,
|
||||
const nsAString& aOptions, nsPIDOMWindowOuter** _retval);
|
||||
const nsAString& aOptions,
|
||||
mozilla::dom::BrowsingContext** _retval);
|
||||
|
||||
virtual mozilla::EventListenerManager* GetExistingListenerManager()
|
||||
const override;
|
||||
|
@ -565,7 +566,8 @@ class nsGlobalWindowOuter final : public mozilla::dom::EventTarget,
|
|||
mozilla::ErrorResult& aError);
|
||||
nsresult Open(const nsAString& aUrl, const nsAString& aName,
|
||||
const nsAString& aOptions, nsDocShellLoadState* aLoadState,
|
||||
bool aForceNoOpener, nsPIDOMWindowOuter** _retval) override;
|
||||
bool aForceNoOpener,
|
||||
mozilla::dom::BrowsingContext** _retval) override;
|
||||
mozilla::dom::Navigator* GetNavigator() override;
|
||||
|
||||
#if defined(MOZ_WIDGET_ANDROID)
|
||||
|
@ -634,7 +636,7 @@ class nsGlobalWindowOuter final : public mozilla::dom::EventTarget,
|
|||
mozilla::ErrorResult& aError);
|
||||
nsresult OpenDialog(const nsAString& aUrl, const nsAString& aName,
|
||||
const nsAString& aOptions, nsISupports* aExtraArgument,
|
||||
nsPIDOMWindowOuter** _retval) override;
|
||||
mozilla::dom::BrowsingContext** _retval) override;
|
||||
void UpdateCommands(const nsAString& anAction, mozilla::dom::Selection* aSel,
|
||||
int16_t aReason) override;
|
||||
|
||||
|
@ -760,9 +762,9 @@ class nsGlobalWindowOuter final : public mozilla::dom::EventTarget,
|
|||
// Window Control Functions
|
||||
|
||||
// Outer windows only.
|
||||
virtual nsresult OpenNoNavigate(const nsAString& aUrl, const nsAString& aName,
|
||||
const nsAString& aOptions,
|
||||
nsPIDOMWindowOuter** _retval) override;
|
||||
virtual nsresult OpenNoNavigate(
|
||||
const nsAString& aUrl, const nsAString& aName, const nsAString& aOptions,
|
||||
mozilla::dom::BrowsingContext** _retval) override;
|
||||
|
||||
private:
|
||||
explicit nsGlobalWindowOuter(uint64_t aWindowID);
|
||||
|
@ -822,7 +824,7 @@ class nsGlobalWindowOuter final : public mozilla::dom::EventTarget,
|
|||
bool aDoJSFixups, bool aNavigate, nsIArray* argv,
|
||||
nsISupports* aExtraArgument,
|
||||
nsDocShellLoadState* aLoadState, bool aForceNoOpener,
|
||||
nsPIDOMWindowOuter** aReturn);
|
||||
mozilla::dom::BrowsingContext** aReturn);
|
||||
|
||||
// Checks that the channel was loaded by the URI currently loaded in aDoc
|
||||
static bool SameLoadingURI(Document* aDoc, nsIChannel* aChannel);
|
||||
|
|
|
@ -1010,7 +1010,7 @@ class nsPIDOMWindowOuter : public mozIDOMWindowProxy {
|
|||
*/
|
||||
virtual nsresult OpenNoNavigate(const nsAString& aUrl, const nsAString& aName,
|
||||
const nsAString& aOptions,
|
||||
nsPIDOMWindowOuter** _retval) = 0;
|
||||
mozilla::dom::BrowsingContext** _retval) = 0;
|
||||
|
||||
/**
|
||||
* Fire a popup blocked event on the document.
|
||||
|
@ -1049,11 +1049,11 @@ class nsPIDOMWindowOuter : public mozIDOMWindowProxy {
|
|||
virtual nsresult Open(const nsAString& aUrl, const nsAString& aName,
|
||||
const nsAString& aOptions,
|
||||
nsDocShellLoadState* aLoadState, bool aForceNoOpener,
|
||||
nsPIDOMWindowOuter** _retval) = 0;
|
||||
mozilla::dom::BrowsingContext** _retval) = 0;
|
||||
virtual nsresult OpenDialog(const nsAString& aUrl, const nsAString& aName,
|
||||
const nsAString& aOptions,
|
||||
nsISupports* aExtraArgument,
|
||||
nsPIDOMWindowOuter** _retval) = 0;
|
||||
mozilla::dom::BrowsingContext** _retval) = 0;
|
||||
|
||||
virtual nsresult GetInnerWidth(int32_t* aWidth) = 0;
|
||||
virtual nsresult GetInnerHeight(int32_t* aHeight) = 0;
|
||||
|
|
|
@ -219,8 +219,8 @@ BrowserElementParent::OpenWindowInProcess(BrowsingContext* aOpenerWindow,
|
|||
nsIURI* aURI, const nsAString& aName,
|
||||
const nsACString& aFeatures,
|
||||
bool aForceNoOpener,
|
||||
mozIDOMWindowProxy** aReturnWindow) {
|
||||
*aReturnWindow = nullptr;
|
||||
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>
|
||||
|
@ -267,11 +267,9 @@ BrowserElementParent::OpenWindowInProcess(BrowsingContext* aOpenerWindow,
|
|||
nsCOMPtr<nsIDocShell> docshell = frameLoader->GetDocShell(IgnoreErrors());
|
||||
NS_ENSURE_TRUE(docshell, BrowserElementParent::OPEN_WINDOW_IGNORED);
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> window = docshell->GetWindow();
|
||||
window.forget(aReturnWindow);
|
||||
docshell->GetBrowsingContext(aReturnBC);
|
||||
|
||||
return !!*aReturnWindow ? opened
|
||||
: BrowserElementParent::OPEN_WINDOW_CANCELLED;
|
||||
return *aReturnBC ? opened : BrowserElementParent::OPEN_WINDOW_CANCELLED;
|
||||
}
|
||||
|
||||
} // namespace mozilla
|
||||
|
|
|
@ -107,7 +107,7 @@ class BrowserElementParent {
|
|||
static OpenWindowResult OpenWindowInProcess(
|
||||
mozilla::dom::BrowsingContext* aOpenerWindow, nsIURI* aURI,
|
||||
const nsAString& aName, const nsACString& aFeatures, bool aForceNoOpener,
|
||||
mozIDOMWindowProxy** aReturnWindow);
|
||||
mozilla::dom::BrowsingContext** aReturnBC);
|
||||
|
||||
private:
|
||||
static OpenWindowResult DispatchOpenWindowEvent(
|
||||
|
|
|
@ -149,9 +149,8 @@ class WebProgressListener final : public nsIWebProgressListener,
|
|||
NS_IMPL_ISUPPORTS(WebProgressListener, nsIWebProgressListener,
|
||||
nsISupportsWeakReference);
|
||||
|
||||
nsresult OpenWindow(const ClientOpenWindowArgs& aArgs,
|
||||
nsPIDOMWindowOuter** aWindow) {
|
||||
MOZ_DIAGNOSTIC_ASSERT(aWindow);
|
||||
nsresult OpenWindow(const ClientOpenWindowArgs& aArgs, BrowsingContext** aBC) {
|
||||
MOZ_DIAGNOSTIC_ASSERT(aBC);
|
||||
|
||||
// [[1. Let url be the result of parsing url with entry settings object's API
|
||||
// base URL.]]
|
||||
|
@ -226,9 +225,10 @@ nsresult OpenWindow(const ClientOpenWindowArgs& aArgs,
|
|||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
nsCOMPtr<nsPIDOMWindowOuter> pwindow = nsPIDOMWindowOuter::From(newWindow);
|
||||
pwindow.forget(aWindow);
|
||||
MOZ_DIAGNOSTIC_ASSERT(*aWindow);
|
||||
RefPtr<BrowsingContext> bc(
|
||||
nsPIDOMWindowOuter::From(newWindow)->GetBrowsingContext());
|
||||
bc.forget(aBC);
|
||||
MOZ_DIAGNOSTIC_ASSERT(*aBC);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
@ -254,20 +254,8 @@ nsresult OpenWindow(const ClientOpenWindowArgs& aArgs,
|
|||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsCOMPtr<mozIDOMWindowProxy> win;
|
||||
rv = bwin->OpenURI(uri, nullptr, nsIBrowserDOMWindow::OPEN_DEFAULTWINDOW,
|
||||
nsIBrowserDOMWindow::OPEN_NEW, principal, csp,
|
||||
getter_AddRefs(win));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
NS_ENSURE_STATE(win);
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> pWin = nsPIDOMWindowOuter::From(win);
|
||||
pWin.forget(aWindow);
|
||||
MOZ_DIAGNOSTIC_ASSERT(*aWindow);
|
||||
|
||||
return NS_OK;
|
||||
return bwin->OpenURI(uri, nullptr, nsIBrowserDOMWindow::OPEN_DEFAULTWINDOW,
|
||||
nsIBrowserDOMWindow::OPEN_NEW, principal, csp, aBC);
|
||||
}
|
||||
|
||||
void WaitForLoad(const ClientOpenWindowArgs& aArgs,
|
||||
|
@ -390,8 +378,10 @@ RefPtr<ClientOpPromise> ClientOpenWindowInCurrentProcess(
|
|||
java::GeckoApp::LaunchOrBringToFront();
|
||||
#endif // MOZ_WIDGET_ANDROID
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> outerWindow;
|
||||
nsresult rv = OpenWindow(aArgs, getter_AddRefs(outerWindow));
|
||||
RefPtr<BrowsingContext> bc;
|
||||
nsresult rv = OpenWindow(aArgs, getter_AddRefs(bc));
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> outerWindow(bc->GetDOMWindow());
|
||||
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
// If we get the NOT_AVAILABLE error that means the browser is still
|
||||
|
@ -402,12 +392,17 @@ RefPtr<ClientOpPromise> ClientOpenWindowInCurrentProcess(
|
|||
p->Then(
|
||||
SystemGroup::EventTargetFor(TaskCategory::Other), __func__,
|
||||
[aArgs, promise](bool aResult) {
|
||||
nsCOMPtr<nsPIDOMWindowOuter> outerWindow;
|
||||
nsresult rv = OpenWindow(aArgs, getter_AddRefs(outerWindow));
|
||||
RefPtr<BrowsingContext> bc;
|
||||
nsresult rv = OpenWindow(aArgs, getter_AddRefs(bc));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
promise->Reject(rv, __func__);
|
||||
return;
|
||||
}
|
||||
nsCOMPtr<nsPIDOMWindowOuter> outerWindow(bc->GetDOMWindow());
|
||||
if (NS_WARN_IF(!outerWindow)) {
|
||||
promise->Reject(NS_ERROR_FAILURE, __func__);
|
||||
return;
|
||||
}
|
||||
|
||||
WaitForLoad(aArgs, outerWindow, promise);
|
||||
},
|
||||
|
|
|
@ -11,6 +11,7 @@ interface nsIURI;
|
|||
interface nsIPrincipal;
|
||||
interface nsIContentSecurityPolicy;
|
||||
interface nsIReferrerInfo;
|
||||
webidl BrowsingContext;
|
||||
webidl Element;
|
||||
|
||||
[scriptable, uuid(e774db14-79ac-4156-a7a3-aa3fd0a22c10)]
|
||||
|
@ -115,7 +116,7 @@ interface nsIBrowserDOMWindow : nsISupports
|
|||
* @param aCsp the CSP to use (if any) for the new window.
|
||||
* @return the window into which the URI would have been opened.
|
||||
*/
|
||||
mozIDOMWindowProxy
|
||||
BrowsingContext
|
||||
createContentWindow(in nsIURI aURI, in mozIDOMWindowProxy aOpener,
|
||||
in short aWhere, in long aFlags,
|
||||
in nsIPrincipal aTriggeringPrincipal,
|
||||
|
@ -150,7 +151,7 @@ interface nsIBrowserDOMWindow : nsISupports
|
|||
* @param aCsp the CSP to be applied to the new load.
|
||||
* @return the window into which the URI was opened.
|
||||
*/
|
||||
mozIDOMWindowProxy
|
||||
BrowsingContext
|
||||
openURI(in nsIURI aURI, in mozIDOMWindowProxy aOpener,
|
||||
in short aWhere, in long aFlags, in nsIPrincipal aTriggeringPrincipal,
|
||||
[optional] in nsIContentSecurityPolicy aCsp);
|
||||
|
|
|
@ -55,6 +55,7 @@
|
|||
#include "mozilla/Move.h"
|
||||
#include "mozilla/PresShell.h"
|
||||
#include "mozilla/ProcessHangMonitor.h"
|
||||
#include "mozilla/ResultExtensions.h"
|
||||
#include "mozilla/ScopeExit.h"
|
||||
#include "mozilla/Services.h"
|
||||
#include "mozilla/StaticPtr.h"
|
||||
|
@ -903,7 +904,7 @@ BrowserChild::ProvideWindow(mozIDOMWindowProxy* aParent, uint32_t aChromeFlags,
|
|||
const nsAString& aName, const nsACString& aFeatures,
|
||||
bool aForceNoOpener, bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState, bool* aWindowIsNew,
|
||||
mozIDOMWindowProxy** aReturn) {
|
||||
BrowsingContext** aReturn) {
|
||||
*aReturn = nullptr;
|
||||
|
||||
// If aParent is inside an <iframe mozbrowser> and this isn't a request to
|
||||
|
@ -926,7 +927,14 @@ BrowserChild::ProvideWindow(mozIDOMWindowProxy* aParent, uint32_t aChromeFlags,
|
|||
if (openLocation == nsIBrowserDOMWindow::OPEN_CURRENTWINDOW) {
|
||||
nsCOMPtr<nsIWebBrowser> browser = do_GetInterface(WebNavigation());
|
||||
*aWindowIsNew = false;
|
||||
return browser->GetContentDOMWindow(aReturn);
|
||||
|
||||
nsCOMPtr<mozIDOMWindowProxy> win;
|
||||
MOZ_TRY(browser->GetContentDOMWindow(getter_AddRefs(win)));
|
||||
|
||||
RefPtr<BrowsingContext> bc(
|
||||
nsPIDOMWindowOuter::From(win)->GetBrowsingContext());
|
||||
bc.forget(aReturn);
|
||||
return NS_OK;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -771,7 +771,7 @@ ContentChild::ProvideWindow(mozIDOMWindowProxy* aParent, uint32_t aChromeFlags,
|
|||
const nsAString& aName, const nsACString& aFeatures,
|
||||
bool aForceNoOpener, bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState, bool* aWindowIsNew,
|
||||
mozIDOMWindowProxy** aReturn) {
|
||||
BrowsingContext** aReturn) {
|
||||
return ProvideWindowCommon(
|
||||
nullptr, aParent, false, aChromeFlags, aCalledFromJS, aPositionSpecified,
|
||||
aSizeSpecified, aURI, aName, aFeatures, aForceNoOpener, aForceNoReferrer,
|
||||
|
@ -860,7 +860,7 @@ nsresult ContentChild::ProvideWindowCommon(
|
|||
bool aSizeSpecified, nsIURI* aURI, const nsAString& aName,
|
||||
const nsACString& aFeatures, bool aForceNoOpener, bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState, bool* aWindowIsNew,
|
||||
mozIDOMWindowProxy** aReturn) {
|
||||
BrowsingContext** aReturn) {
|
||||
*aReturn = nullptr;
|
||||
|
||||
nsAutoPtr<IPCTabContext> ipcContext;
|
||||
|
@ -1104,9 +1104,10 @@ nsresult ContentChild::ProvideWindowCommon(
|
|||
newChild->RecvLoadURL(urlToLoad, showInfo);
|
||||
}
|
||||
|
||||
nsCOMPtr<mozIDOMWindowProxy> win =
|
||||
nsCOMPtr<nsPIDOMWindowOuter> win =
|
||||
do_GetInterface(newChild->WebNavigation());
|
||||
win.forget(aReturn);
|
||||
RefPtr<BrowsingContext> bc(win->GetBrowsingContext());
|
||||
bc.forget(aReturn);
|
||||
};
|
||||
|
||||
// NOTE: Capturing by reference here is safe, as this function won't return
|
||||
|
|
|
@ -104,13 +104,15 @@ class ContentChild final : public PContentChild,
|
|||
nsCString sourceURL;
|
||||
};
|
||||
|
||||
nsresult ProvideWindowCommon(
|
||||
BrowserChild* aTabOpener, mozIDOMWindowProxy* aParent, bool aIframeMoz,
|
||||
uint32_t aChromeFlags, bool aCalledFromJS, bool aPositionSpecified,
|
||||
bool aSizeSpecified, nsIURI* aURI, const nsAString& aName,
|
||||
const nsACString& aFeatures, bool aForceNoOpener, bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState, bool* aWindowIsNew,
|
||||
mozIDOMWindowProxy** aReturn);
|
||||
nsresult ProvideWindowCommon(BrowserChild* aTabOpener,
|
||||
mozIDOMWindowProxy* aParent, bool aIframeMoz,
|
||||
uint32_t aChromeFlags, bool aCalledFromJS,
|
||||
bool aPositionSpecified, bool aSizeSpecified,
|
||||
nsIURI* aURI, const nsAString& aName,
|
||||
const nsACString& aFeatures, bool aForceNoOpener,
|
||||
bool aForceNoReferrer,
|
||||
nsDocShellLoadState* aLoadState,
|
||||
bool* aWindowIsNew, BrowsingContext** aReturn);
|
||||
|
||||
bool Init(MessageLoop* aIOLoop, base::ProcessId aParentPid,
|
||||
const char* aParentBuildID, IPC::Channel* aChannel,
|
||||
|
|
|
@ -4882,11 +4882,11 @@ mozilla::ipc::IPCResult ContentParent::CommonCreateWindow(
|
|||
aResult = NS_ERROR_ABORT;
|
||||
return IPC_OK();
|
||||
}
|
||||
nsCOMPtr<mozIDOMWindowProxy> win;
|
||||
RefPtr<BrowsingContext> bc;
|
||||
aResult = newBrowserDOMWin->OpenURI(
|
||||
aURIToLoad, openerWindow, nsIBrowserDOMWindow::OPEN_CURRENTWINDOW,
|
||||
nsIBrowserDOMWindow::OPEN_NEW, aTriggeringPrincipal, aCsp,
|
||||
getter_AddRefs(win));
|
||||
getter_AddRefs(bc));
|
||||
}
|
||||
|
||||
return IPC_OK();
|
||||
|
|
|
@ -4224,7 +4224,7 @@ nsBrowserAccess.prototype = {
|
|||
aTriggeringPrincipal,
|
||||
aCsp
|
||||
);
|
||||
return browser && browser.contentWindow;
|
||||
return browser && browser.browsingContext;
|
||||
},
|
||||
|
||||
createContentWindow: function browser_createContentWindow(
|
||||
|
@ -4243,7 +4243,7 @@ nsBrowserAccess.prototype = {
|
|||
aTriggeringPrincipal,
|
||||
aCsp
|
||||
);
|
||||
return browser && browser.contentWindow;
|
||||
return browser && browser.browsingContext;
|
||||
},
|
||||
|
||||
openURIInFrame: function browser_openURIInFrame(
|
||||
|
|
|
@ -359,7 +359,7 @@ class GeckoViewNavigation extends GeckoViewModule {
|
|||
return null;
|
||||
}
|
||||
|
||||
return browser.contentWindow;
|
||||
return browser.browsingContext;
|
||||
}
|
||||
|
||||
// nsIBrowserDOMWindow.
|
||||
|
@ -474,7 +474,7 @@ class GeckoViewNavigation extends GeckoViewModule {
|
|||
null,
|
||||
null
|
||||
);
|
||||
return browser && browser.contentWindow;
|
||||
return browser && browser.browsingContext;
|
||||
}
|
||||
|
||||
// nsIBrowserDOMWindow.
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
|
||||
#include "nsPrintProgress.h"
|
||||
|
||||
#include "mozilla/dom/BrowsingContext.h"
|
||||
#include "nsArray.h"
|
||||
#include "nsIBaseWindow.h"
|
||||
#include "nsIDocShell.h"
|
||||
|
@ -82,12 +83,12 @@ NS_IMETHODIMP nsPrintProgress::OpenProgressDialog(
|
|||
nsPIDOMWindowOuter::From(ownerWindow);
|
||||
|
||||
// Open the dialog.
|
||||
nsCOMPtr<nsPIDOMWindowOuter> newWindow;
|
||||
RefPtr<mozilla::dom::BrowsingContext> newBC;
|
||||
|
||||
rv = piOwnerWindow->OpenDialog(
|
||||
NS_ConvertASCIItoUTF16(dialogURL), NS_LITERAL_STRING("_blank"),
|
||||
NS_LITERAL_STRING("chrome,titlebar,dependent,centerscreen"), array,
|
||||
getter_AddRefs(newWindow));
|
||||
getter_AddRefs(newBC));
|
||||
}
|
||||
|
||||
return rv;
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
class nsDocShellLoadState;
|
||||
%}
|
||||
|
||||
webidl BrowsingContext;
|
||||
interface mozIDOMWindowProxy;
|
||||
interface nsIURI;
|
||||
native nsDocShellLoadStatePtr(nsDocShellLoadState*);
|
||||
|
@ -97,16 +98,16 @@ interface nsIWindowProvider : nsISupports
|
|||
* @see nsIWindowWatcher for more information on aFeatures.
|
||||
* @see nsIWebBrowserChrome for more information on aChromeFlags.
|
||||
*/
|
||||
mozIDOMWindowProxy provideWindow(in mozIDOMWindowProxy aParent,
|
||||
in unsigned long aChromeFlags,
|
||||
in boolean aCalledFromJS,
|
||||
in boolean aPositionSpecified,
|
||||
in boolean aSizeSpecified,
|
||||
in nsIURI aURI,
|
||||
in AString aName,
|
||||
in AUTF8String aFeatures,
|
||||
in boolean aForceNoOpener,
|
||||
in boolean aForceNoReferrer,
|
||||
in nsDocShellLoadStatePtr aLoadState,
|
||||
out boolean aWindowIsNew);
|
||||
BrowsingContext provideWindow(in mozIDOMWindowProxy aParent,
|
||||
in unsigned long aChromeFlags,
|
||||
in boolean aCalledFromJS,
|
||||
in boolean aPositionSpecified,
|
||||
in boolean aSizeSpecified,
|
||||
in nsIURI aURI,
|
||||
in AString aName,
|
||||
in AUTF8String aFeatures,
|
||||
in boolean aForceNoOpener,
|
||||
in boolean aForceNoReferrer,
|
||||
in nsDocShellLoadStatePtr aLoadState,
|
||||
out boolean aWindowIsNew);
|
||||
};
|
||||
|
|
|
@ -15,7 +15,6 @@ interface nsIWebBrowserChrome;
|
|||
interface nsIWindowCreator;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* nsIWindowWatcher is the keeper of Gecko/DOM Windows. It maintains
|
||||
* a list of open top-level windows, and allows some operations on them.
|
||||
|
|
|
@ -758,15 +758,14 @@ nsresult nsWindowWatcher::OpenWindowInternal(
|
|||
}
|
||||
|
||||
if (provider) {
|
||||
nsCOMPtr<mozIDOMWindowProxy> newWindow;
|
||||
RefPtr<BrowsingContext> newBC;
|
||||
rv = provider->ProvideWindow(
|
||||
aParent, chromeFlags, aCalledFromJS, sizeSpec.PositionSpecified(),
|
||||
sizeSpec.SizeSpecified(), uriToLoad, name, features, aForceNoOpener,
|
||||
aForceNoReferrer, aLoadState, &windowIsNew,
|
||||
getter_AddRefs(newWindow));
|
||||
aForceNoReferrer, aLoadState, &windowIsNew, getter_AddRefs(newBC));
|
||||
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
GetWindowTreeItem(newWindow, getter_AddRefs(newDocShellItem));
|
||||
if (NS_SUCCEEDED(rv) && newBC) {
|
||||
newDocShellItem = newBC->GetDocShell();
|
||||
if (windowIsNew && newDocShellItem) {
|
||||
// Make sure to stop any loads happening in this window that the
|
||||
// window provider might have started. Otherwise if our caller
|
||||
|
@ -783,7 +782,7 @@ nsresult nsWindowWatcher::OpenWindowInternal(
|
|||
if (!windowIsNew && newDocShellItem) {
|
||||
nsCOMPtr<nsIDocShell> docShell = do_QueryInterface(newDocShellItem);
|
||||
if (!CheckUserContextCompatibility(docShell)) {
|
||||
newWindow = nullptr;
|
||||
newBC = nullptr;
|
||||
newDocShellItem = nullptr;
|
||||
windowIsNew = false;
|
||||
}
|
||||
|
|
|
@ -704,7 +704,7 @@ nsContentTreeOwner::ProvideWindow(
|
|||
bool aPositionSpecified, bool aSizeSpecified, nsIURI* aURI,
|
||||
const nsAString& aName, const nsACString& aFeatures, bool aForceNoOpener,
|
||||
bool aForceNoReferrer, nsDocShellLoadState* aLoadState, bool* aWindowIsNew,
|
||||
mozIDOMWindowProxy** aReturn) {
|
||||
BrowsingContext** aReturn) {
|
||||
NS_ENSURE_ARG_POINTER(aParent);
|
||||
|
||||
auto* parentWin = nsPIDOMWindowOuter::From(aParent);
|
||||
|
|
Загрузка…
Ссылка в новой задаче