Firefox · DOM
CVE-2026-117883
Logic Error in DOM
Overview
High
Severity
—
CVSS
No
Exploited ITW
Fixed
Fix Status
Changed Functions
| Function | Change | Notes |
|---|---|---|
ifdom/xhr/XMLHttpRequestMainThread.cpp |
modified |
Files Changed
dom/xhr/XMLHttpRequestMainThread.cppparser/html/nsHtml5StreamParser.cpp
Patch
diff --git a/dom/xhr/XMLHttpRequestMainThread.cpp b/dom/xhr/XMLHttpRequestMainThread.cpp
index 71eee59ba93..0e1cd90df03 100644
--- a/dom/xhr/XMLHttpRequestMainThread.cpp
+++ b/dom/xhr/XMLHttpRequestMainThread.cpp
@@ -390,6 +390,16 @@ void XMLHttpRequestMainThread::SetAssociatedBrowsingContextID(uint64_t aId) {
}
void XMLHttpRequestMainThread::ResetResponse() {
+ if (RefPtr<nsXHRParseEndListener> listener = mParseEndListener.forget()) {
+ if (mResponseXML) {
+ if (EventListenerManager* manager =
+ mResponseXML->GetExistingListenerManager()) {
+ manager->RemoveEventListenerByType(listener,
+ kLiteralString_DOMContentLoaded,
+ TrustedEventsAtSystemGroupBubble());
+ }
+ }
+ }
mResponseXML = nullptr;
mResponseBody.Truncate();
TruncateResponseText();
@@ -1051,6 +1061,9 @@ void XMLHttpRequestMainThread::CloseRequest(nsresult detail) {
"XMLHttpRequestMainThread::CloseRequest"_ns);
}
CancelTimeoutTimer();
+ if (mResponseXML) {
+ mResponseXML->StopDocumentLoad();
+ }
}
void XMLHttpRequestMainThread::CloseRequestWithError(
@@ -2009,6 +2022,30 @@ XMLHttpRequestMainThread::OnStartRequest(nsIRequest* request) {
ChangeState(XMLHttpRequest_Binding::HEADERS_RECEIVED);
}
+ // Re-run earlier check after scripts may have changed the state.
+
+ if (request != mChannel) {
+ // Can this still happen?
+ return NS_OK;
+ }
+
+ // Don't do anything if we have been aborted
+ if (mState == XMLHttpRequest_Binding::UNSENT) {
+ return NS_OK;
+ }
+
+ // Don't do anything if we're in mid-abort, but let the request
+ // know (this can happen due to race conditions in valid XHRs,
+ // see bz1070763 for info).
+ if (mFlagAborted) {
+ return NS_BINDING_ABORTED;
+ }
+
+ // Don't do anything if we have timed out.
+ if (mFlagTimedOut) {
+ return NS_OK;
+ }
+
ResetResponse();
if (!mOverrideMimeType.IsEmpty()) {
diff --git a/parser/html/nsHtml5StreamParser.cpp b/parser/html/nsHtml5StreamParser.cpp
index 16d212cf5f6..9191a8b1bf6 100644
--- a/parser/html/nsHtml5StreamParser.cpp
+++ b/parser/html/nsHtml5StreamParser.cpp
@@ -110,11 +110,24 @@ NS_IMPL_CYCLE_COLLECTION_CLASS(nsHtml5StreamParser)
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(nsHtml5StreamParser)
tmp->DropTimer();
+ tmp->Terminate();
NS_IMPL_CYCLE_COLLECTION_UNLINK(mRequest)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mOwner)
- tmp->mExecutorFlusher = nullptr;
- tmp->mLoadFlusher = nullptr;
- tmp->mExecutor = nullptr;
+
+ // At this point, tasks on the parser thread can still
+ // execute. We have a mechanism for making sure that the
+ // stream parser stays alive for long enough. However, the
+ // way tree ops make their way into the executor happens
+ // through non-owning references, so we must not allow
+ // `mExecutor` to be deleted too early.
+ // `mExecutor` itself is a plain pointer, because
+ // `mLoadFlusher`, and `mExecutorFlusher` hold strong
+ // refs. Even though cycle collection traversal goes
+ // through them to discover a cycle, we deliberately
+ // don't set them to `nullptr` here to make sure that
+ // the executor stays around for as long as the stream
+ // parser stays around. We trust the cycle to be broken
+ // at some other edge of the cycle.
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(nsHtml5StreamParser)
Loading diff…
References
On This Page