Merge mozilla-central to autoland. a=merge CLOSED TREE
authorGurzau Raul <rgurzau@mozilla.com>
Mon, 15 Oct 2018 01:20:42 +0300
changeset 499634 e55f454f1ab6e08c0464d65bd48a3a51bf16aab3
parent 499633 c98344b84b2004021a883f43a1adf66d203a128e (current diff)
parent 499626 3aca49b2df240e86d5b164feb18575681c818c63 (diff)
child 499635 8bf31628742de6153ce9c2ff1ebc16d69b8d605d
push id1864
push userffxbld-merge
push dateMon, 03 Dec 2018 15:51:40 +0000
treeherdermozilla-release@f040763d99ad [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmerge
milestone64.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Merge mozilla-central to autoland. a=merge CLOSED TREE
--- a/browser/base/content/test/general/browser_homeDrop.js
+++ b/browser/base/content/test/general/browser_homeDrop.js
@@ -14,18 +14,16 @@ add_task(async function() {
   ok(dragSrcElement, "Downloads button exists");
   let homeButton = document.getElementById("home-button");
   ok(homeButton, "home button present");
 
   async function drop(dragData, homepage) {
     let setHomepageDialogPromise = BrowserTestUtils.domWindowOpened();
 
     EventUtils.synthesizeDrop(dragSrcElement, homeButton, dragData, "copy", window);
-    // Ensure dnd suppression is cleared.
-    EventUtils.synthesizeMouseAtCenter(homeButton, { type: "mouseup" }, window);
 
     let setHomepageDialog = await setHomepageDialogPromise;
     ok(true, "dialog appeared in response to home button drop");
     await BrowserTestUtils.waitForEvent(setHomepageDialog, "load", false);
 
     let setHomepagePromise = new Promise(function(resolve) {
       let observer = {
         QueryInterface: ChromeUtils.generateQI([Ci.nsIObserver]),
@@ -65,18 +63,16 @@ add_task(async function() {
       });
 
       executeSoon(function() {
         info("Attempting second drop, of a javascript: URI");
         // The drop handler throws an exception when dragging URIs that inherit
         // principal, e.g. javascript:
         expectUncaughtException();
         EventUtils.synthesizeDrop(dragSrcElement, homeButton, [[{type: "text/plain", data: "javascript:8888"}]], "copy", window);
-        // Ensure dnd suppression is cleared.
-        EventUtils.synthesizeMouseAtCenter(homeButton, { type: "mouseup" }, window);
       });
     });
   }
 
   await drop([[{type: "text/plain",
                  data: "http://mochi.test:8888/"}]],
               "http://mochi.test:8888/");
   await drop([[{type: "text/plain",
--- a/browser/components/customizableui/test/head.js
+++ b/browser/components/customizableui/test/head.js
@@ -18,17 +18,17 @@ Services.scriptloader.loadSubScript("chr
 /**
  * Instance of CustomizableUITestUtils for the current browser window.
  */
 var gCUITestUtils = new CustomizableUITestUtils(window);
 
 Services.prefs.setBoolPref("browser.uiCustomization.skipSourceNodeCheck", true);
 registerCleanupFunction(() => Services.prefs.clearUserPref("browser.uiCustomization.skipSourceNodeCheck"));
 
-var {synthesizeDragStart, synthesizeDrop, synthesizeMouseAtCenter} = EventUtils;
+var {synthesizeDragStart, synthesizeDrop} = EventUtils;
 
 const kNSXUL = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
 
 const kForceOverflowWidthPx = 300;
 
 function createDummyXULButton(id, label, win = window) {
   let btn = document.createElementNS(kNSXUL, "toolbarbutton");
   btn.id = id;
@@ -184,18 +184,16 @@ function simulateItemDrag(aToDrag, aTarg
       ev = {clientX: bounds.right - 2, clientY: bounds.bottom - 2};
     } else {
       ev = {clientX: bounds.left + 2, clientY: bounds.top + 2};
     }
   }
   ev._domDispatchOnly = true;
   synthesizeDrop(aToDrag.parentNode, aTarget, null, null,
                  aToDrag.ownerGlobal, aTarget.ownerGlobal, ev);
-  // Ensure dnd suppression is cleared.
-  synthesizeMouseAtCenter(aTarget, { type: "mouseup" }, aTarget.ownerGlobal);
 }
 
 function endCustomizing(aWindow = window) {
   if (aWindow.document.documentElement.getAttribute("customizing") != "true") {
     return true;
   }
   return new Promise(resolve => {
     function onCustomizationEnds() {
--- a/docshell/base/nsDocShell.cpp
+++ b/docshell/base/nsDocShell.cpp
@@ -1799,27 +1799,29 @@ nsDocShell::GetAffectPrivateSessionLifet
 NS_IMETHODIMP
 nsDocShell::AddWeakPrivacyTransitionObserver(
     nsIPrivacyTransitionObserver* aObserver)
 {
   nsWeakPtr weakObs = do_GetWeakReference(aObserver);
   if (!weakObs) {
     return NS_ERROR_NOT_AVAILABLE;
   }
-  return mPrivacyObservers.AppendElement(weakObs) ? NS_OK : NS_ERROR_FAILURE;
+  mPrivacyObservers.AppendElement(weakObs);
+  return NS_OK;
 }
 
 NS_IMETHODIMP
 nsDocShell::AddWeakReflowObserver(nsIReflowObserver* aObserver)
 {
   nsWeakPtr weakObs = do_GetWeakReference(aObserver);
   if (!weakObs) {
     return NS_ERROR_FAILURE;
   }
-  return mReflowObservers.AppendElement(weakObs) ? NS_OK : NS_ERROR_FAILURE;
+  mReflowObservers.AppendElement(weakObs);
+  return NS_OK;
 }
 
 NS_IMETHODIMP
 nsDocShell::RemoveWeakReflowObserver(nsIReflowObserver* aObserver)
 {
   nsWeakPtr obs = do_GetWeakReference(aObserver);
   return mReflowObservers.RemoveElement(obs) ? NS_OK : NS_ERROR_FAILURE;
 }
@@ -2510,17 +2512,18 @@ nsDocShell::GetCurrentDocChannel()
 
 NS_IMETHODIMP
 nsDocShell::AddWeakScrollObserver(nsIScrollObserver* aObserver)
 {
   nsWeakPtr weakObs = do_GetWeakReference(aObserver);
   if (!weakObs) {
     return NS_ERROR_FAILURE;
   }
-  return mScrollObservers.AppendElement(weakObs) ? NS_OK : NS_ERROR_FAILURE;
+  mScrollObservers.AppendElement(weakObs);
+  return NS_OK;
 }
 
 NS_IMETHODIMP
 nsDocShell::RemoveWeakScrollObserver(nsIScrollObserver* aObserver)
 {
   nsWeakPtr obs = do_GetWeakReference(aObserver);
   return mScrollObservers.RemoveElement(obs) ? NS_OK : NS_ERROR_FAILURE;
 }
--- a/docshell/shistory/nsSHistory.cpp
+++ b/docshell/shistory/nsSHistory.cpp
@@ -777,18 +777,18 @@ nsSHistory::AddSHistoryListener(nsISHist
   // Check if the listener supports Weak Reference. This is a must.
   // This listener functionality is used by embedders and we want to
   // have the right ownership with who ever listens to SHistory
   nsWeakPtr listener = do_GetWeakReference(aListener);
   if (!listener) {
     return NS_ERROR_FAILURE;
   }
 
-  return mListeners.AppendElementUnlessExists(listener) ?
-    NS_OK : NS_ERROR_OUT_OF_MEMORY;
+  mListeners.AppendElementUnlessExists(listener);
+  return NS_OK;
 }
 
 NS_IMETHODIMP
 nsSHistory::RemoveSHistoryListener(nsISHistoryListener* aListener)
 {
   // Make sure the listener that wants to be removed is the
   // one we have in store.
   nsWeakPtr listener = do_GetWeakReference(aListener);
--- a/dom/base/nsDocument.cpp
+++ b/dom/base/nsDocument.cpp
@@ -2095,19 +2095,17 @@ nsDocument::Init()
 
   // Force initialization.
   nsINode::nsSlots* slots = Slots();
 
   // Prepend self as mutation-observer whether we need it or not (some
   // subclasses currently do, other don't). This is because the code in
   // nsNodeUtils always notifies the first observer first, expecting the
   // first observer to be the document.
-  NS_ENSURE_TRUE(slots->mMutationObservers.PrependElementUnlessExists(static_cast<nsIMutationObserver*>(this)),
-                 NS_ERROR_OUT_OF_MEMORY);
-
+  slots->mMutationObservers.PrependElementUnlessExists(static_cast<nsIMutationObserver*>(this));
 
   mOnloadBlocker = new nsOnloadBlocker();
   mCSSLoader = new mozilla::css::Loader(this);
   // Assume we're not quirky, until we know otherwise
   mCSSLoader->SetCompatibilityMode(eCompatibility_FullStandards);
 
   mStyleImageLoader = new mozilla::css::ImageLoader(this);
 
--- a/dom/ipc/CoalescedMouseData.cpp
+++ b/dom/ipc/CoalescedMouseData.cpp
@@ -83,19 +83,17 @@ CoalescedMouseMoveFlusher::StartObserver
   nsRefreshDriver* refreshDriver = GetRefreshDriver();
   if (mRefreshDriver && mRefreshDriver == refreshDriver) {
     // Nothing to do if we already added an observer and it's same refresh driver.
     return;
   }
   RemoveObserver();
   if (refreshDriver) {
     mRefreshDriver = refreshDriver;
-    DebugOnly<bool> success =
-      mRefreshDriver->AddRefreshObserver(this, FlushType::Event);
-    MOZ_ASSERT(success);
+    mRefreshDriver->AddRefreshObserver(this, FlushType::Event);
   }
 }
 
 void
 CoalescedMouseMoveFlusher::RemoveObserver()
 {
   if (mRefreshDriver) {
     mRefreshDriver->RemoveRefreshObserver(this, FlushType::Event);
--- a/dom/xml/nsXMLContentSink.cpp
+++ b/dom/xml/nsXMLContentSink.cpp
@@ -314,18 +314,18 @@ nsXMLContentSink::DidBuildModel(bool aTe
 
     bool startLayout = true;
 
     if (mPrettyPrinting) {
       NS_ASSERTION(!mPendingSheetCount, "Shouldn't have pending sheets here!");
 
       // We're pretty-printing now.  See whether we should wait up on
       // stylesheet loads
-      if (mDocument->CSSLoader()->HasPendingLoads() &&
-          NS_SUCCEEDED(mDocument->CSSLoader()->AddObserver(this))) {
+      if (mDocument->CSSLoader()->HasPendingLoads()) {
+        mDocument->CSSLoader()->AddObserver(this);
         // wait for those sheets to load
         startLayout = false;
       }
     }
 
     if (startLayout) {
       StartLayout(false);
 
--- a/layout/base/PresShell.cpp
+++ b/layout/base/PresShell.cpp
@@ -5558,22 +5558,18 @@ void PresShell::SynthesizeMouseMove(bool
 
   if (mMouseLocation == nsPoint(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE))
     return;
 
   if (!mSynthMouseMoveEvent.IsPending()) {
     RefPtr<nsSynthMouseMoveEvent> ev =
         new nsSynthMouseMoveEvent(this, aFromScroll);
 
-    if (!GetPresContext()->RefreshDriver()
-                         ->AddRefreshObserver(ev, FlushType::Display)) {
-      NS_WARNING("failed to dispatch nsSynthMouseMoveEvent");
-      return;
-    }
-
+    GetPresContext()->RefreshDriver()
+                    ->AddRefreshObserver(ev, FlushType::Display);
     mSynthMouseMoveEvent = std::move(ev);
   }
 }
 
 /**
  * Find the first floating view with a widget in a postorder traversal of the
  * view tree that contains the point. Thus more deeply nested floating views
  * are preferred over their ancestors, and floating views earlier in the
@@ -9411,18 +9407,21 @@ PresShell::Observe(nsISupports* aSubject
   return NS_ERROR_FAILURE;
 }
 
 bool
 nsIPresShell::AddRefreshObserver(nsARefreshObserver* aObserver,
                                  FlushType aFlushType)
 {
   nsPresContext* presContext = GetPresContext();
-  return presContext &&
-      presContext->RefreshDriver()->AddRefreshObserver(aObserver, aFlushType);
+  if (MOZ_UNLIKELY(!presContext)) {
+    return false;
+  }
+  presContext->RefreshDriver()->AddRefreshObserver(aObserver, aFlushType);
+  return true;
 }
 
 bool
 nsIPresShell::RemoveRefreshObserver(nsARefreshObserver* aObserver,
                                     FlushType aFlushType)
 {
   nsPresContext* presContext = GetPresContext();
   return presContext &&
--- a/layout/base/nsRefreshDriver.cpp
+++ b/layout/base/nsRefreshDriver.cpp
@@ -1199,49 +1199,47 @@ nsRefreshDriver::MostRecentRefresh() con
   // RestyleManager::ProcessPendingRestyles().
   if (!ServoStyleSet::IsInServoTraversal()) {
     const_cast<nsRefreshDriver*>(this)->EnsureTimerStarted();
   }
 
   return mMostRecentRefresh;
 }
 
-bool
+void
 nsRefreshDriver::AddRefreshObserver(nsARefreshObserver* aObserver,
                                     FlushType aFlushType)
 {
   ObserverArray& array = ArrayFor(aFlushType);
-  bool success = array.AppendElement(aObserver) != nullptr;
+  array.AppendElement(aObserver);
   EnsureTimerStarted();
-  return success;
 }
 
 bool
 nsRefreshDriver::RemoveRefreshObserver(nsARefreshObserver* aObserver,
                                        FlushType aFlushType)
 {
   ObserverArray& array = ArrayFor(aFlushType);
   return array.RemoveElement(aObserver);
 }
 
-bool
+void
 nsRefreshDriver::AddTimerAdjustmentObserver(
-  nsATimerAdjustmentObserver *aObserver)
+  nsATimerAdjustmentObserver* aObserver)
 {
   MOZ_ASSERT(!mTimerAdjustmentObservers.Contains(aObserver));
-
-  return mTimerAdjustmentObservers.AppendElement(aObserver) != nullptr;
+  mTimerAdjustmentObservers.AppendElement(aObserver);
 }
 
-bool
+void
 nsRefreshDriver::RemoveTimerAdjustmentObserver(
-  nsATimerAdjustmentObserver *aObserver)
+  nsATimerAdjustmentObserver* aObserver)
 {
   MOZ_ASSERT(mTimerAdjustmentObservers.Contains(aObserver));
-  return mTimerAdjustmentObservers.RemoveElement(aObserver);
+  mTimerAdjustmentObservers.RemoveElement(aObserver);
 }
 
 void
 nsRefreshDriver::PostScrollEvent(mozilla::Runnable* aScrollEvent)
 {
   mScrollEvents.AppendElement(aScrollEvent);
   EnsureTimerStarted();
 }
--- a/layout/base/nsRefreshDriver.h
+++ b/layout/base/nsRefreshDriver.h
@@ -115,43 +115,43 @@ public:
    * used by callers who want to start an animation now and want to know
    * what time to consider the start of the animation.  (This helps
    * ensure that multiple animations started during the same event off
    * the main event loop have the same start time.)
    */
   mozilla::TimeStamp MostRecentRefresh() const;
 
   /**
-   * Add / remove refresh observers.  Returns whether the operation
-   * succeeded.
+   * Add / remove refresh observers.
+   * RemoveRefreshObserver returns true if aObserver was found.
    *
    * The flush type affects:
    *   + the order in which the observers are notified (lowest flush
    *     type to highest, in order registered)
    *   + (in the future) which observers are suppressed when the display
    *     doesn't require current position data or isn't currently
    *     painting, and, correspondingly, which get notified when there
    *     is a flush during such suppression
    * and it must be FlushType::Style, FlushType::Layout, or FlushType::Display.
    *
    * The refresh driver does NOT own a reference to these observers;
    * they must remove themselves before they are destroyed.
    *
    * The observer will be called even if there is no other activity.
    */
-  bool AddRefreshObserver(nsARefreshObserver *aObserver,
+  void AddRefreshObserver(nsARefreshObserver* aObserver,
                           mozilla::FlushType aFlushType);
-  bool RemoveRefreshObserver(nsARefreshObserver *aObserver,
+  bool RemoveRefreshObserver(nsARefreshObserver* aObserver,
                              mozilla::FlushType aFlushType);
   /**
    * Add / remove an observer wants to know the time when the refresh driver
    * updated the most recent refresh time due to its active timer changes.
    */
-  bool AddTimerAdjustmentObserver(nsATimerAdjustmentObserver *aObserver);
-  bool RemoveTimerAdjustmentObserver(nsATimerAdjustmentObserver *aObserver);
+  void AddTimerAdjustmentObserver(nsATimerAdjustmentObserver* aObserver);
+  void RemoveTimerAdjustmentObserver(nsATimerAdjustmentObserver* aObserver);
 
   void PostScrollEvent(mozilla::Runnable* aScrollEvent);
   void DispatchScrollEvents();
 
   /**
    * Add an observer that will be called after each refresh. The caller
    * must remove the observer before it is deleted. This does not trigger
    * refresh driver ticks.
--- a/layout/generic/nsGfxScrollFrame.cpp
+++ b/layout/generic/nsGfxScrollFrame.cpp
@@ -1836,27 +1836,22 @@ public:
     // The callback may release "this".
     // We don't access members after returning, so no need for KungFuDeathGrip.
     ScrollFrameHelper::AsyncSmoothMSDScrollCallback(mCallee, deltaTime);
   }
 
   /*
    * Set a refresh observer for smooth scroll iterations (and start observing).
    * Should be used at most once during the lifetime of this object.
-   * Return value: true on success, false otherwise.
    */
-  bool SetRefreshObserver(ScrollFrameHelper *aCallee) {
+  void SetRefreshObserver(ScrollFrameHelper* aCallee) {
     NS_ASSERTION(aCallee && !mCallee, "AsyncSmoothMSDScroll::SetRefreshObserver - Invalid usage.");
 
-    if (!RefreshDriver(aCallee)->AddRefreshObserver(this, FlushType::Style)) {
-      return false;
-    }
-
+    RefreshDriver(aCallee)->AddRefreshObserver(this, FlushType::Style);
     mCallee = aCallee;
-    return true;
   }
 
   /**
    * The mCallee holds a strong ref to us since the refresh driver doesn't.
    * Our dtor and mCallee's Destroy() method both call RemoveObserver() -
    * whichever comes first removes us from the refresh driver.
    */
   void RemoveObserver() {
@@ -1949,30 +1944,25 @@ private:
 // The next section is observer/callback management
 // Bodies of WillRefresh and RefreshDriver contain ScrollFrameHelper specific code.
 public:
   NS_INLINE_DECL_REFCOUNTING(AsyncScroll, override)
 
   /*
    * Set a refresh observer for smooth scroll iterations (and start observing).
    * Should be used at most once during the lifetime of this object.
-   * Return value: true on success, false otherwise.
    */
-  bool SetRefreshObserver(ScrollFrameHelper *aCallee) {
+  void SetRefreshObserver(ScrollFrameHelper* aCallee) {
     NS_ASSERTION(aCallee && !mCallee, "AsyncScroll::SetRefreshObserver - Invalid usage.");
 
-    if (!RefreshDriver(aCallee)->AddRefreshObserver(this, FlushType::Style)) {
-      return false;
-    }
-
+    RefreshDriver(aCallee)->AddRefreshObserver(this, FlushType::Style);
     mCallee = aCallee;
     nsIPresShell* shell = mCallee->mOuter->PresShell();
     MOZ_ASSERT(shell);
     shell->SuppressDisplayport(true);
-    return true;
   }
 
   virtual void WillRefresh(mozilla::TimeStamp aTime) override {
     // The callback may release "this".
     // We don't access members after returning, so no need for KungFuDeathGrip.
     ScrollFrameHelper::AsyncScrollCallback(mCallee, aTime);
   }
 
@@ -2465,21 +2455,17 @@ ScrollFrameHelper::ScrollToWithOrigin(ns
           return;
         }
 
         mAsyncSmoothMSDScroll =
           new AsyncSmoothMSDScroll(GetScrollPosition(), mDestination,
                                    currentVelocity, GetScrollRangeForClamping(),
                                    now, presContext);
 
-        if (!mAsyncSmoothMSDScroll->SetRefreshObserver(this)) {
-          // Observer setup failed. Scroll the normal way.
-          CompleteAsyncScroll(range, aOrigin);
-          return;
-        }
+        mAsyncSmoothMSDScroll->SetRefreshObserver(this);
       } else {
         // A previous smooth MSD scroll is still in progress, so we just need to
         // update its range and destination.
         mAsyncSmoothMSDScroll->SetRange(GetScrollRangeForClamping());
         mAsyncSmoothMSDScroll->SetDestination(mDestination);
       }
 
       return;
@@ -2488,21 +2474,17 @@ ScrollFrameHelper::ScrollToWithOrigin(ns
         currentVelocity = mAsyncSmoothMSDScroll->GetVelocity();
         mAsyncSmoothMSDScroll = nullptr;
       }
     }
   }
 
   if (!mAsyncScroll) {
     mAsyncScroll = new AsyncScroll();
-    if (!mAsyncScroll->SetRefreshObserver(this)) {
-      // Observer setup failed. Scroll the normal way.
-      CompleteAsyncScroll(range, aOrigin);
-      return;
-    }
+    mAsyncScroll->SetRefreshObserver(this);
   }
 
   if (isSmoothScroll) {
     mAsyncScroll->InitSmoothScroll(now, GetScrollPosition(), mDestination,
                                    aOrigin, range, currentVelocity);
   } else {
     mAsyncScroll->Init(range);
   }
--- a/layout/style/Loader.cpp
+++ b/layout/style/Loader.cpp
@@ -2565,25 +2565,21 @@ Loader::HasPendingLoads()
 {
   return
     (mSheets && mSheets->mLoadingDatas.Count() != 0) ||
     (mSheets && mSheets->mPendingDatas.Count() != 0) ||
     mPostedEvents.Length() != 0 ||
     mDatasToNotifyOn != 0;
 }
 
-nsresult
+void
 Loader::AddObserver(nsICSSLoaderObserver* aObserver)
 {
   MOZ_ASSERT(aObserver, "Must have observer");
-  if (mObservers.AppendElementUnlessExists(aObserver)) {
-    return NS_OK;
-  }
-
-  return NS_ERROR_OUT_OF_MEMORY;
+  mObservers.AppendElementUnlessExists(aObserver);
 }
 
 void
 Loader::RemoveObserver(nsICSSLoaderObserver* aObserver)
 {
   mObservers.RemoveElement(aObserver);
 }
 
--- a/layout/style/Loader.h
+++ b/layout/style/Loader.h
@@ -424,17 +424,17 @@ public:
    * Add an observer to this loader.  The observer will be notified
    * for all loads that would have notified their own observers (even
    * if those loads don't have observers attached to them).
    * Load-specific observers will be notified before generic
    * observers.  The loader holds a reference to the observer.
    *
    * aObserver must not be null.
    */
-  nsresult AddObserver(nsICSSLoaderObserver* aObserver);
+  void AddObserver(nsICSSLoaderObserver* aObserver);
 
   /**
    * Remove an observer added via AddObserver.
    */
   void RemoveObserver(nsICSSLoaderObserver* aObserver);
 
   // These interfaces are public only for the benefit of static functions
   // within nsCSSLoader.cpp.
--- a/testing/mochitest/tests/SimpleTest/EventUtils.js
+++ b/testing/mochitest/tests/SimpleTest/EventUtils.js
@@ -2330,16 +2330,18 @@ function synthesizeDropAfterDragOver(aRe
   if (aResult) {
     effect = "none";
   } else if (effect != "none") {
     event = createDragEventObject("drop", aDestElement, aDestWindow,
                                   aDataTransfer, aDragEvent);
     sendDragEvent(event, aDestElement, aDestWindow);
   }
 
+  synthesizeMouseAtCenter(aDestElement, { type: "mouseup" }, aDestWindow);
+
   return effect;
 }
 
 /**
  * Emulate a drag and drop by emulating a dragstart and firing events dragenter,
  * dragover, and drop.
  *
  * @param aSrcElement   The element to use to start the drag.
@@ -2458,16 +2460,17 @@ async function synthesizePlainDragAndDro
     await new Promise(r => setTimeout(r, 0));
 
     event = createDragEventObject("drop", destElement, destWindow,
                                   dataTransfer, {});
     sendDragEvent(event, destElement, destWindow);
 
     await new Promise(r => setTimeout(r, 0));
 
+    synthesizeMouseAtCenter(destElement, { type: "mouseup" }, destWindow);
   } finally {
     ds.endDragSession(true, 0);
   }
 }
 
 var PluginUtils =
 {
   withTestPlugin : function(callback)
--- a/toolkit/components/places/History.cpp
+++ b/toolkit/components/places/History.cpp
@@ -2311,21 +2311,17 @@ History::RegisterVisitedCallback(nsIURI*
   }
 
   // Sanity check that Links are not registered more than once for a given URI.
   // This will not catch a case where it is registered for two different URIs.
   NS_ASSERTION(!observers.Contains(aLink),
                "Already tracking this Link object!");
 
   // Start tracking our Link.
-  if (!observers.AppendElement(aLink)) {
-    // Curses - unregister and return failure.
-    (void)UnregisterVisitedCallback(aURI, aLink);
-    return NS_ERROR_OUT_OF_MEMORY;
-  }
+  observers.AppendElement(aLink);
 
   // If this link has already been visited, we cannot synchronously mark
   // ourselves as visited, so instead we fire a runnable into our docgroup,
   // which will handle it for us.
   if (key->mVisited) {
     DispatchNotifyVisited(aURI, GetLinkDocument(aLink));
   }
 
--- a/uriloader/base/nsDocLoader.cpp
+++ b/uriloader/base/nsDocLoader.cpp
@@ -638,21 +638,18 @@ nsresult nsDocLoader::RemoveChildLoader(
   if (NS_SUCCEEDED(rv)) {
     rv = aChild->SetDocLoaderParent(nullptr);
   }
   return rv;
 }
 
 nsresult nsDocLoader::AddChildLoader(nsDocLoader* aChild)
 {
-  nsresult rv = mChildList.AppendElement(aChild) ? NS_OK : NS_ERROR_OUT_OF_MEMORY;
-  if (NS_SUCCEEDED(rv)) {
-    rv = aChild->SetDocLoaderParent(this);
-  }
-  return rv;
+  mChildList.AppendElement(aChild);
+  return aChild->SetDocLoaderParent(this);
 }
 
 NS_IMETHODIMP nsDocLoader::GetDocumentChannel(nsIChannel ** aChannel)
 {
   if (!mDocumentRequest) {
     *aChannel = nullptr;
     return NS_OK;
   }
@@ -878,18 +875,18 @@ nsDocLoader::AddProgressListener(nsIWebP
     return NS_ERROR_FAILURE;
   }
 
   nsWeakPtr listener = do_GetWeakReference(aListener);
   if (!listener) {
     return NS_ERROR_INVALID_ARG;
   }
 
-  return mListenerInfoList.AppendElement(nsListenerInfo(listener, aNotifyMask)) ?
-         NS_OK : NS_ERROR_OUT_OF_MEMORY;
+  mListenerInfoList.AppendElement(nsListenerInfo(listener, aNotifyMask));
+  return NS_OK;
 }
 
 NS_IMETHODIMP
 nsDocLoader::RemoveProgressListener(nsIWebProgressListener *aListener)
 {
   return mListenerInfoList.RemoveElement(aListener) ? NS_OK : NS_ERROR_FAILURE;
 }
 
--- a/xpcom/ds/nsTObserverArray.h
+++ b/xpcom/ds/nsTObserverArray.h
@@ -170,74 +170,68 @@ public:
 
   //
   // Mutation methods
   //
 
   // Insert a given element at the given index.
   // @param aIndex The index at which to insert item.
   // @param aItem  The item to insert,
-  // @return A pointer to the newly inserted element, or a null on DOM
   template<class Item>
-  elem_type* InsertElementAt(index_type aIndex, const Item& aItem)
+  void InsertElementAt(index_type aIndex, const Item& aItem)
   {
-    elem_type* item = mArray.InsertElementAt(aIndex, aItem);
+    mArray.InsertElementAt(aIndex, aItem);
     AdjustIterators(aIndex, 1);
-    return item;
   }
 
   // Same as above but without copy constructing.
   // This is useful to avoid temporaries.
   elem_type* InsertElementAt(index_type aIndex)
   {
     elem_type* item = mArray.InsertElementAt(aIndex);
     AdjustIterators(aIndex, 1);
     return item;
   }
 
   // Prepend an element to the array unless it already exists in the array.
   // 'operator==' must be defined for elem_type.
   // @param aItem The item to prepend.
-  // @return true if the element was found, or inserted successfully.
   template<class Item>
-  bool PrependElementUnlessExists(const Item& aItem)
+  void PrependElementUnlessExists(const Item& aItem)
   {
-    if (Contains(aItem)) {
-      return true;
+    if (!Contains(aItem)) {
+      mArray.InsertElementAt(0, aItem);
+      AdjustIterators(0, 1);
     }
-
-    bool inserted = mArray.InsertElementAt(0, aItem) != nullptr;
-    AdjustIterators(0, 1);
-    return inserted;
   }
 
   // Append an element to the array.
   // @param aItem The item to append.
-  // @return A pointer to the newly appended element, or null on OOM.
   template<class Item>
-  elem_type* AppendElement(const Item& aItem)
+  void AppendElement(const Item& aItem)
   {
-    return mArray.AppendElement(aItem);
+    mArray.AppendElement(aItem);
   }
 
   // Same as above, but without copy-constructing. This is useful to avoid
   // temporaries.
   elem_type* AppendElement()
   {
     return mArray.AppendElement();
   }
 
   // Append an element to the array unless it already exists in the array.
   // 'operator==' must be defined for elem_type.
   // @param aItem The item to append.
-  // @return true if the element was found, or inserted successfully.
   template<class Item>
-  bool AppendElementUnlessExists(const Item& aItem)
+  void AppendElementUnlessExists(const Item& aItem)
   {
-    return Contains(aItem) || AppendElement(aItem) != nullptr;
+    if (!Contains(aItem)) {
+      mArray.AppendElement(aItem);
+    }
   }
 
   // Remove an element from the array.
   // @param aIndex The index of the item to remove.
   void RemoveElementAt(index_type aIndex)
   {
     NS_ASSERTION(aIndex < mArray.Length(), "invalid index");
     mArray.RemoveElementAt(aIndex);