Bug 1000175. Make sure error events on window only fire if the active document has not changed from when the exception was thrown. r=smaug

This commit is contained in:
Boris Zbarsky 2014-05-20 16:07:17 -04:00
Родитель 7d5dc0457f
Коммит c75678d212
1 изменённых файлов: 16 добавлений и 16 удалений

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

@ -386,10 +386,8 @@ AsyncErrorReporter::AsyncErrorReporter(JSRuntime* aRuntime,
NS_LITERAL_CSTRING("content javascript"); NS_LITERAL_CSTRING("content javascript");
mInnerWindowID = 0; mInnerWindowID = 0;
if (aWindow && aWindow->IsOuterWindow()) {
aWindow = aWindow->GetCurrentInnerWindow();
}
if (aWindow) { if (aWindow) {
MOZ_ASSERT(aWindow->IsInnerWindow());
mInnerWindowID = aWindow->WindowID(); mInnerWindowID = aWindow->WindowID();
} }
} }
@ -427,8 +425,7 @@ AsyncErrorReporter::ReportError()
class ScriptErrorEvent : public AsyncErrorReporter class ScriptErrorEvent : public AsyncErrorReporter
{ {
public: public:
ScriptErrorEvent(nsIScriptGlobalObject* aScriptGlobal, ScriptErrorEvent(JSRuntime* aRuntime,
JSRuntime* aRuntime,
JSErrorReport* aErrorReport, JSErrorReport* aErrorReport,
const char* aFallbackMessage, const char* aFallbackMessage,
nsIPrincipal* aScriptOriginPrincipal, nsIPrincipal* aScriptOriginPrincipal,
@ -440,20 +437,21 @@ public:
: AsyncErrorReporter(aRuntime, aErrorReport, aFallbackMessage, : AsyncErrorReporter(aRuntime, aErrorReport, aFallbackMessage,
nsContentUtils::IsSystemPrincipal(aGlobalPrincipal), nsContentUtils::IsSystemPrincipal(aGlobalPrincipal),
aWindow) aWindow)
, mScriptGlobal(aScriptGlobal)
, mOriginPrincipal(aScriptOriginPrincipal) , mOriginPrincipal(aScriptOriginPrincipal)
, mDispatchEvent(aDispatchEvent) , mDispatchEvent(aDispatchEvent)
, mError(aRuntime, aError) , mError(aRuntime, aError)
, mWindow(aWindow)
{ {
MOZ_ASSERT_IF(mWindow, mWindow->IsInnerWindow());
} }
NS_IMETHOD Run() NS_IMETHOD Run()
{ {
nsEventStatus status = nsEventStatus_eIgnore; nsEventStatus status = nsEventStatus_eIgnore;
// First, notify the DOM that we have a script error. // First, notify the DOM that we have a script error, but only if
if (mDispatchEvent) { // our window is still the current inner, if we're associated with a window.
nsCOMPtr<nsPIDOMWindow> win(do_QueryInterface(mScriptGlobal)); if (mDispatchEvent && (!mWindow || mWindow->IsCurrentInnerWindow())) {
nsIDocShell* docShell = win ? win->GetDocShell() : nullptr; nsIDocShell* docShell = mWindow ? mWindow->GetDocShell() : nullptr;
if (docShell && if (docShell &&
!JSREPORT_IS_WARNING(mFlags) && !JSREPORT_IS_WARNING(mFlags) &&
!sHandlingScriptError) { !sHandlingScriptError) {
@ -469,7 +467,7 @@ public:
init.mFilename = mFileName; init.mFilename = mFileName;
init.mBubbles = true; init.mBubbles = true;
nsCOMPtr<nsIScriptObjectPrincipal> sop(do_QueryInterface(win)); nsCOMPtr<nsIScriptObjectPrincipal> sop(do_QueryInterface(mWindow));
NS_ENSURE_STATE(sop); NS_ENSURE_STATE(sop);
nsIPrincipal* p = sop->GetPrincipal(); nsIPrincipal* p = sop->GetPrincipal();
NS_ENSURE_STATE(p); NS_ENSURE_STATE(p);
@ -495,11 +493,11 @@ public:
} }
nsRefPtr<ErrorEvent> event = nsRefPtr<ErrorEvent> event =
ErrorEvent::Constructor(static_cast<nsGlobalWindow*>(win.get()), ErrorEvent::Constructor(static_cast<nsGlobalWindow*>(mWindow.get()),
NS_LITERAL_STRING("error"), init); NS_LITERAL_STRING("error"), init);
event->SetTrusted(true); event->SetTrusted(true);
EventDispatcher::DispatchDOMEvent(win, nullptr, event, presContext, EventDispatcher::DispatchDOMEvent(mWindow, nullptr, event, presContext,
&status); &status);
} }
} }
@ -512,10 +510,10 @@ public:
} }
private: private:
nsCOMPtr<nsIScriptGlobalObject> mScriptGlobal;
nsCOMPtr<nsIPrincipal> mOriginPrincipal; nsCOMPtr<nsIPrincipal> mOriginPrincipal;
bool mDispatchEvent; bool mDispatchEvent;
JS::PersistentRootedValue mError; JS::PersistentRootedValue mError;
nsCOMPtr<nsPIDOMWindow> mWindow;
static bool sHandlingScriptError; static bool sHandlingScriptError;
}; };
@ -573,13 +571,15 @@ NS_ScriptErrorReporter(JSContext *cx,
if (globalObject) { if (globalObject) {
nsCOMPtr<nsPIDOMWindow> win = do_QueryInterface(globalObject); nsCOMPtr<nsPIDOMWindow> win = do_QueryInterface(globalObject);
if (win) {
win = win->GetCurrentInnerWindow();
}
nsCOMPtr<nsIScriptObjectPrincipal> scriptPrincipal = nsCOMPtr<nsIScriptObjectPrincipal> scriptPrincipal =
do_QueryInterface(globalObject); do_QueryInterface(globalObject);
NS_ASSERTION(scriptPrincipal, "Global objects must implement " NS_ASSERTION(scriptPrincipal, "Global objects must implement "
"nsIScriptObjectPrincipal"); "nsIScriptObjectPrincipal");
nsContentUtils::AddScriptRunner( nsContentUtils::AddScriptRunner(
new ScriptErrorEvent(globalObject, new ScriptErrorEvent(JS_GetRuntime(cx),
JS_GetRuntime(cx),
report, report,
message, message,
nsJSPrincipals::get(report->originPrincipals), nsJSPrincipals::get(report->originPrincipals),