merge mozilla-inbound to mozilla-central a=merge
authorCarsten "Tomcat" Book <cbook@mozilla.com>
Tue, 26 Apr 2016 13:44:45 +0200
changeset 748495 9ce31e9f90cb0e534611b0f617c5bbc232ffe748
parent 748490 f2b20c6eb71dbf7a2884a776251e760e73b8c69b (current diff)
parent 748409 0c4758a01aabcd51330c84ed1deeed7795e8f547 (diff)
child 748496 9cd07d2cca91f58712f1f3dc4f5e040568bd295d
child 748501 fa59214470bc708b33b2e6019a84cd17f8fc7853
child 748529 20d85e25e89971fb20349545bdd0e169d67f2ddb
child 748588 cc8ffd786b06a8966d4da088f56cd66566107312
child 748612 986b29c009a6ad2a3a87266380a97f8cf979a10e
child 748657 c4b5cd84a95ec79db6bcb5e08780b9bfcebc98e3
child 748663 9505b57a54b091b1d0bcbd061fa2e8e9f369ab6a
child 748678 824cfa9c6048ee8ab382c930fb50cb458e5832b7
child 748680 549f1ac3d99fbb6672ec34d356135f423b7026c6
child 748682 5c07f34ea6454874e449a4686827f0d812fe5970
child 748719 7df2bf5cfb191129a2ba20786ca757f62cfed9e8
child 748763 02cc8a304f1391c910836ca221124d941a4b036c
child 748764 65dbeaaaef6817c2cee45c96a0c956d5402b6a77
child 748767 a2927d3488e26328809066aecb794929bf8ce255
child 748776 759837e7d775ad3a59d338ecf735ec4ef27809b3
child 748783 ba04cf88a07ea2417fa051dc15b12678352c77c0
child 748807 7371c3eed60049341c9dfd2f4c7b6d63ccf821bf
child 748837 f334efff1f3c3cd58437f7fb96698d240f899fd4
child 748845 78db4611dbb20bc552a8167091671eaa7cc07888
child 748850 4a9def324e8d199fd79dc7c5c33e05fa8559dad0
child 748875 c6bcb279fd22417dcfcd955d22d52d7c856668d1
child 748935 9bdbe779acf4efebf6ee8819a63475701c9a25fa
child 749081 1d5cf7fb183fe8fac7bdbfbf590258bac875f618
child 749169 09ad64982940fba300d0884045bd22a71a0bd60a
child 749272 98fd6fceb4ccd644f0c8dd8799ec38a2317d3d4e
child 749377 143f01784538d4f181f6b3db54cb2507ee0f946c
child 749383 638496ce961bec9506d45297b18fe74ccc32a02c
child 749402 1e23fc4ca62763222c00bccfdc26f875892732c3
child 749446 befa1b60e50be6af4a3c5488c56db1827f1c7ab0
child 749513 afed95817f81b5c5b738070031c74129c07a9ca8
child 749533 98e2d46f305aff11643d4d1dcfcd8e5fae7d4095
child 750209 ed6218b38af5ff566dad2d1a30bf46ee153ac15f
child 750297 2390c2ec19230a64a203ae9fbf1510c81a14cb6d
child 750533 2dd099cb2bd2d40d799481b78cc6c20cb24f09f5
child 752372 496e6b972d51d1b92853ed63075f4ef17a018869
child 753170 ab36557fe60fe56620e2f53468b6a2bd5def0308
child 753287 9cae253735d2c40e920f1306313a4f02232f686c
child 753559 35001deb49ea33e93da5977df4eb32a409b385c0
push id121456
push usermbanner@mozilla.com
push dateTue, 26 Apr 2016 12:19:20 +0000
treeherdertry@5eb1f3107692 [default view] [failures only]
reviewersmerge
milestone49.0a1
merge mozilla-inbound to mozilla-central a=merge
--- a/accessible/generic/Accessible.cpp
+++ b/accessible/generic/Accessible.cpp
@@ -1763,17 +1763,17 @@ Accessible::RelationByType(RelationType 
 void
 Accessible::GetNativeInterface(void** aNativeAccessible)
 {
 }
 
 void
 Accessible::DoCommand(nsIContent *aContent, uint32_t aActionIndex)
 {
-  class Runnable final : public nsRunnable
+  class Runnable final : public mozilla::Runnable
   {
   public:
     Runnable(Accessible* aAcc, nsIContent* aContent, uint32_t aIdx) :
       mAcc(aAcc), mContent(aContent), mIdx(aIdx) { }
 
     NS_IMETHOD Run() override
     {
       if (mAcc)
--- a/devtools/client/debugger/test/mochitest/browser_dbg_stack-03.js
+++ b/devtools/client/debugger/test/mochitest/browser_dbg_stack-03.js
@@ -3,73 +3,58 @@
 /* Any copyright is dedicated to the Public Domain.
  * http://creativecommons.org/publicdomain/zero/1.0/ */
 
 /**
  * Test that stackframes are scrollable.
  */
 
 const TAB_URL = EXAMPLE_URL + "doc_recursion-stack.html";
-
-var gTab, gDebuggee, gPanel, gDebugger;
-var gFrames, gClassicFrames, gFramesScrollingInterval;
+let framesScrollingInterval;
 
 function test() {
   initDebugger(TAB_URL).then(([aTab, aDebuggee, aPanel]) => {
-    gTab = aTab;
-    gDebuggee = aDebuggee;
-    gPanel = aPanel;
-    gDebugger = gPanel.panelWin;
-    gFrames = gDebugger.DebuggerView.StackFrames;
-    gClassicFrames = gDebugger.DebuggerView.StackFramesClassicList;
+    const tab = aTab;
+    const debuggee = aDebuggee;
+    const panel = aPanel;
+    const gDebugger = panel.panelWin;
+    const frames = gDebugger.DebuggerView.StackFrames;
+    const classicFrames = gDebugger.DebuggerView.StackFramesClassicList;
+
+    Task.spawn(function*() {
+      framesScrollingInterval = window.setInterval(() => {
+        frames.widget._list.scrollByIndex(-1);
+      }, 100);
+
+      yield waitForDebuggerEvents(panel, gDebugger.EVENTS.AFTER_FRAMES_REFILLED);
+
+      is(gDebugger.gThreadClient.state, "paused",
+        "Should only be getting stack frames while paused.");
+      is(frames.itemCount, gDebugger.gCallStackPageSize,
+        "Should have only the max limit of frames.");
+      is(classicFrames.itemCount, gDebugger.gCallStackPageSize,
+        "Should have only the max limit of frames in the mirrored view as well.");
+
+      yield waitForDebuggerEvents(panel, gDebugger.EVENTS.AFTER_FRAMES_REFILLED);
+
+      is(frames.itemCount, gDebugger.gCallStackPageSize * 2,
+        "Should now have twice the max limit of frames.");
+      is(classicFrames.itemCount, gDebugger.gCallStackPageSize * 2,
+        "Should now have twice the max limit of frames in the mirrored view as well.");
+
+      yield waitForDebuggerEvents(panel, gDebugger.EVENTS.AFTER_FRAMES_REFILLED);
+
+      is(frames.itemCount, debuggee.gRecurseLimit,
+        "Should have reached the recurse limit.");
+      is(classicFrames.itemCount, debuggee.gRecurseLimit,
+        "Should have reached the recurse limit in the mirrored view as well.");
 
 
-    waitForDebuggerEvents(gPanel, gDebugger.EVENTS.AFTER_FRAMES_REFILLED)
-      .then(performTest);
+      // Call stack frame scrolling should stop before
+      // we resume the gDebugger as it could be a source of race conditions.
+      window.clearInterval(framesScrollingInterval);
+      resumeDebuggerThenCloseAndFinish(panel);
+    });
 
-    gDebuggee.gRecurseLimit = (gDebugger.gCallStackPageSize * 2) + 1;
-    gDebuggee.recurse();
+    debuggee.gRecurseLimit = (gDebugger.gCallStackPageSize * 2) + 1;
+    debuggee.recurse();
   });
 }
-
-function performTest() {
-  is(gDebugger.gThreadClient.state, "paused",
-    "Should only be getting stack frames while paused.");
-  is(gFrames.itemCount, gDebugger.gCallStackPageSize,
-    "Should have only the max limit of frames.");
-  is(gClassicFrames.itemCount, gDebugger.gCallStackPageSize,
-    "Should have only the max limit of frames in the mirrored view as well.");
-
-  waitForDebuggerEvents(gPanel, gDebugger.EVENTS.AFTER_FRAMES_REFILLED).then(() => {
-    is(gFrames.itemCount, gDebugger.gCallStackPageSize * 2,
-      "Should now have twice the max limit of frames.");
-    is(gClassicFrames.itemCount, gDebugger.gCallStackPageSize * 2,
-      "Should now have twice the max limit of frames in the mirrored view as well.");
-
-    waitForDebuggerEvents(gPanel, gDebugger.EVENTS.AFTER_FRAMES_REFILLED).then(() => {
-      is(gFrames.itemCount, gDebuggee.gRecurseLimit,
-        "Should have reached the recurse limit.");
-      is(gClassicFrames.itemCount, gDebuggee.gRecurseLimit,
-        "Should have reached the recurse limit in the mirrored view as well.");
-
-      gDebugger.gThreadClient.resume(() => {
-        window.clearInterval(gFramesScrollingInterval);
-        closeDebuggerAndFinish(gPanel);
-      });
-    });
-  });
-
-  gFramesScrollingInterval = window.setInterval(() => {
-    gFrames.widget._list.scrollByIndex(-1);
-  }, 100);
-}
-
-registerCleanupFunction(function() {
-  window.clearInterval(gFramesScrollingInterval);
-  gFramesScrollingInterval = null;
-
-  gTab = null;
-  gDebuggee = null;
-  gPanel = null;
-  gDebugger = null;
-  gFrames = null;
-  gClassicFrames = null;
-});
--- a/devtools/client/framework/test/browser.ini
+++ b/devtools/client/framework/test/browser.ini
@@ -75,11 +75,10 @@ skip-if = e10s # Bug 1069044 - destroyIn
 [browser_toolbox_view_source_04.js]
 [browser_toolbox_window_reload_target.js]
 [browser_toolbox_window_shortcuts.js]
 skip-if = os == "mac" && os_version == "10.8" || os == "win" && os_version == "5.1" # Bug 851129 - Re-enable browser_toolbox_window_shortcuts.js test after leaks are fixed
 [browser_toolbox_window_title_changes.js]
 [browser_toolbox_window_title_frame_select.js]
 [browser_toolbox_zoom.js]
 [browser_two_tabs.js]
-skip-if = e10s && debug && os == 'win' # Bug 1231869
 # We want this test to run for mochitest-dt as well, so we include it here:
 [../../../../browser/base/content/test/general/browser_parsable_css.js]
--- a/devtools/client/inspector/markup/test/browser.ini
+++ b/devtools/client/inspector/markup/test/browser.ini
@@ -50,37 +50,36 @@ support-files =
 [browser_markup_anonymous_02.js]
 skip-if = e10s # scratchpad.xul is not loading in e10s window
 [browser_markup_anonymous_03.js]
 [browser_markup_anonymous_04.js]
 [browser_markup_copy_image_data.js]
 [browser_markup_css_completion_style_attribute_01.js]
 [browser_markup_css_completion_style_attribute_02.js]
 [browser_markup_dragdrop_autoscroll.js]
-skip-if = e10s && os == 'win'
 [browser_markup_dragdrop_distance.js]
 [browser_markup_dragdrop_draggable.js]
 [browser_markup_dragdrop_dragRootNode.js]
 [browser_markup_dragdrop_escapeKeyPress.js]
 [browser_markup_dragdrop_invalidNodes.js]
 [browser_markup_dragdrop_reorder.js]
 [browser_markup_dragdrop_tooltip.js]
 [browser_markup_events.js]
 [browser_markup_events_form.js]
-# [browser_markup_events-overflow.js]
-# disabled - See bug 1177550
 [browser_markup_events_jquery_1.0.js]
 [browser_markup_events_jquery_1.1.js]
 [browser_markup_events_jquery_1.2.js]
 [browser_markup_events_jquery_1.3.js]
 [browser_markup_events_jquery_1.4.js]
 [browser_markup_events_jquery_1.6.js]
 [browser_markup_events_jquery_1.7.js]
 [browser_markup_events_jquery_1.11.1.js]
 [browser_markup_events_jquery_2.1.1.js]
+[browser_markup_events-overflow.js]
+skip-if = true # Bug 1177550
 [browser_markup_links_01.js]
 [browser_markup_links_02.js]
 [browser_markup_links_03.js]
 [browser_markup_links_04.js]
 [browser_markup_links_05.js]
 [browser_markup_links_06.js]
 [browser_markup_links_07.js]
 [browser_markup_load_01.js]
--- a/devtools/client/shadereditor/test/browser.ini
+++ b/devtools/client/shadereditor/test/browser.ini
@@ -29,31 +29,19 @@ skip-if = true # Bug 942473, caused by B
 [browser_se_shaders-edit-03.js]
 [browser_webgl-actor-test-01.js]
 [browser_webgl-actor-test-02.js]
 [browser_webgl-actor-test-03.js]
 [browser_webgl-actor-test-04.js]
 [browser_webgl-actor-test-05.js]
 [browser_webgl-actor-test-06.js]
 [browser_webgl-actor-test-07.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-08.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-09.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-10.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-11.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-12.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-13.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-14.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-15.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-16.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-17.js]
-skip-if = e10s && os == 'win'
 [browser_webgl-actor-test-18.js]
-skip-if = e10s && os == 'win'
--- a/docshell/base/nsDocShell.cpp
+++ b/docshell/base/nsDocShell.cpp
@@ -9456,17 +9456,17 @@ nsDocShell::CopyFavicon(nsIURI* aOldURI,
       new nsCopyFaviconCallback(favSvc, aNewURI,
                                 aLoadingPrincipal,
                                 aInPrivateBrowsing);
     favSvc->GetFaviconURLForPage(aOldURI, callback);
   }
 #endif
 }
 
-class InternalLoadEvent : public nsRunnable
+class InternalLoadEvent : public Runnable
 {
 public:
   InternalLoadEvent(nsDocShell* aDocShell, nsIURI* aURI,
                     nsIURI* aOriginalURI, bool aLoadReplace,
                     nsIURI* aReferrer, uint32_t aReferrerPolicy,
                     nsISupports* aOwner, uint32_t aFlags,
                     const char* aTypeHint, nsIInputStream* aPostData,
                     nsIInputStream* aHeadersData, uint32_t aLoadType,
@@ -13519,17 +13519,17 @@ nsDocShell::SelectAll(void)
 NS_IMETHODIMP
 nsDocShell::SelectNone(void)
 {
   return DoCommand("cmd_selectNone");
 }
 
 // link handling
 
-class OnLinkClickEvent : public nsRunnable
+class OnLinkClickEvent : public Runnable
 {
 public:
   OnLinkClickEvent(nsDocShell* aHandler, nsIContent* aContent,
                    nsIURI* aURI,
                    const char16_t* aTargetSpec,
                    const nsAString& aFileName,
                    nsIInputStream* aPostDataStream,
                    nsIInputStream* aHeadersDataStream,
--- a/docshell/base/nsDocShell.h
+++ b/docshell/base/nsDocShell.h
@@ -754,17 +754,17 @@ protected:
   {
     bool didDisplayLoadError = false;
     DisplayLoadError(aError, aURI, aURL, aFailedChannel, &didDisplayLoadError);
     return didDisplayLoadError;
   }
 
 public:
   // Event type dispatched by RestorePresentation
-  class RestorePresentationEvent : public nsRunnable
+  class RestorePresentationEvent : public mozilla::Runnable
   {
   public:
     NS_DECL_NSIRUNNABLE
     explicit RestorePresentationEvent(nsDocShell* aDs) : mDocShell(aDs) {}
     void Revoke() { mDocShell = nullptr; }
   private:
     RefPtr<nsDocShell> mDocShell;
   };
--- a/docshell/shistory/nsSHEntryShared.cpp
+++ b/docshell/shistory/nsSHEntryShared.cpp
@@ -243,17 +243,17 @@ nsSHEntryShared::RemoveFromBFCacheSync()
 
   if (viewer) {
     viewer->Destroy();
   }
 
   return NS_OK;
 }
 
-class DestroyViewerEvent : public nsRunnable
+class DestroyViewerEvent : public mozilla::Runnable
 {
 public:
   DestroyViewerEvent(nsIContentViewer* aViewer, nsIDocument* aDocument)
     : mViewer(aViewer)
     , mDocument(aDocument)
   {
   }
 
--- a/docshell/test/navigation/mochitest.ini
+++ b/docshell/test/navigation/mochitest.ini
@@ -23,33 +23,28 @@ support-files =
   open.html
   parent.html
 
 [test_bug13871.html]
 skip-if = buildapp == 'b2g' || buildapp == 'mulet' || toolkit == 'android' #RANDOM # Bug 1136180 disabled on B2G Desktop and Mulet for intermittent failures
 [test_bug270414.html]
 skip-if = buildapp == 'b2g' || buildapp == 'mulet' || toolkit == "android" # Bug 1136180 disabled on B2G Desktop and Mulet for intermittent failures
 [test_bug278916.html]
-skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop specific, initial triage
 [test_bug279495.html]
-skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop specific, initial triage
 [test_bug344861.html]
-skip-if = buildapp == "mulet" || buildapp == "b2g" || toolkit == "android" || toolkit == "windows" # disabled on Windows because of bug 1234520
+skip-if = buildapp == 'b2g' || buildapp == 'mulet' || toolkit == "android" || toolkit == "windows" # disabled on Windows because of bug 1234520
 [test_bug386782.html]
-skip-if = (buildapp == 'b2g' && (toolkit != 'gonk' || debug))
 [test_bug430624.html]
 [test_bug430723.html]
-skip-if = (buildapp == 'b2g' && (toolkit != 'gonk' || debug)) || toolkit == 'android' #TIMED_OUT # b2g-debug(bug 874423) b2g-desktop(Bug 931116, b2g desktop specific, initial triage)
+skip-if = (buildapp == 'b2g' && debug) || toolkit == 'android' #TIMED_OUT # b2g-debug(bug 874423) b2g-desktop(Bug 931116, b2g desktop specific, initial triage)
 [test_child.html]
 [test_grandchild.html]
 [test_not-opener.html]
 skip-if = buildapp == 'b2g'
 [test_opener.html]
-skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop specific, initial triage
 [test_popup-navigates-children.html]
 skip-if = buildapp == 'b2g' # b2g(Needs multiple window.open support, also uses docshelltreenode) b2g-debug(Needs multiple window.open support, also uses docshelltreenode) b2g-desktop(Needs multiple window.open support, also uses docshelltreenode)
 [test_reserved.html]
-skip-if = (buildapp == 'b2g' && (toolkit != 'gonk' || debug)) || (toolkit == 'android') #too slow on Android 4.3 aws only; bug 1030403
+skip-if = (buildapp == 'b2g' && debug) || (toolkit == 'android') || (debug && e10s) #too slow on Android 4.3 aws only; bug 1030403; bug 1263213 for debug e10s
 [test_sessionhistory.html]
-skip-if = (buildapp == 'b2g' && (toolkit != 'gonk' || debug)) || toolkit == 'android' #RANDOM # b2g-debug(Perma-orange on debug emulator builds) b2g-desktop(Bug 931116, b2g desktop specific, initial triage)
+skip-if = (buildapp == 'b2g' && debug) || toolkit == 'android' #RANDOM # b2g-debug(Perma-orange on debug emulator builds) b2g-desktop(Bug 931116, b2g desktop specific, initial triage)
 [test_sibling-matching-parent.html]
 [test_sibling-off-domain.html]
-skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop specific, initial triage
--- a/dom/archivereader/ArchiveEvent.h
+++ b/dom/archivereader/ArchiveEvent.h
@@ -44,17 +44,17 @@ protected:
   nsCString mType;
 };
 
 /**
  * This class must be extended by any archive format supported by ArchiveReader API
  * This class runs in a different thread and it calls the 'exec()' method.
  * The exec() must populate mFileList and mStatus then it must call RunShare();
  */
-class ArchiveReaderEvent : public nsRunnable
+class ArchiveReaderEvent : public Runnable
 {
 public:
   NS_DECL_NSIRUNNABLE
 
   explicit ArchiveReaderEvent(ArchiveReader* aArchiveReader);
 
 protected:
   virtual ~ArchiveReaderEvent();
--- a/dom/archivereader/ArchiveRequest.cpp
+++ b/dom/archivereader/ArchiveRequest.cpp
@@ -13,17 +13,17 @@
 
 using namespace mozilla;
 
 USING_ARCHIVEREADER_NAMESPACE
 
 /**
  * Class used to make asynchronous the ArchiveRequest.
  */
-class ArchiveRequestEvent : public nsRunnable
+class ArchiveRequestEvent : public Runnable
 {
 public:
   NS_DECL_NSIRUNNABLE
 
   explicit ArchiveRequestEvent(ArchiveRequest* aRequest)
   : mRequest(aRequest)
   {
     MOZ_COUNT_CTOR(ArchiveRequestEvent);
--- a/dom/asmjscache/AsmJSCache.cpp
+++ b/dom/asmjscache/AsmJSCache.cpp
@@ -233,17 +233,17 @@ EvictEntries(nsIFile* aDirectory, const 
 
     entry.clear();
   }
 }
 
 // FileDescriptorHolder owns a file descriptor and its memory mapping.
 // FileDescriptorHolder is derived by two runnable classes (that is,
 // (Parent|Child)Runnable.
-class FileDescriptorHolder : public nsRunnable
+class FileDescriptorHolder : public Runnable
 {
 public:
   FileDescriptorHolder()
   : mQuotaObject(nullptr),
     mFileSize(INT64_MIN),
     mFileDesc(nullptr),
     mFileMap(nullptr),
     mMappedMemory(nullptr)
--- a/dom/audiochannel/AudioChannelService.cpp
+++ b/dom/audiochannel/AudioChannelService.cpp
@@ -38,17 +38,17 @@ using namespace mozilla::dom;
 using namespace mozilla::hal;
 
 namespace {
 
 // If true, any new AudioChannelAgent will be muted when created.
 bool sAudioChannelMutedByDefault = false;
 bool sXPCOMShuttingDown = false;
 
-class NotifyChannelActiveRunnable final : public nsRunnable
+class NotifyChannelActiveRunnable final : public Runnable
 {
 public:
   NotifyChannelActiveRunnable(uint64_t aWindowID, AudioChannel aAudioChannel,
                               bool aActive)
     : mWindowID(aWindowID)
     , mAudioChannel(aAudioChannel)
     , mActive(aActive)
   {}
@@ -93,28 +93,28 @@ private:
   const AudioChannel mAudioChannel;
   const bool mActive;
 };
 
 void
 NotifyChannelActive(uint64_t aWindowID, AudioChannel aAudioChannel,
                     bool aActive)
 {
-  RefPtr<nsRunnable> runnable =
+  RefPtr<Runnable> runnable =
     new NotifyChannelActiveRunnable(aWindowID, aAudioChannel, aActive);
   NS_DispatchToCurrentThread(runnable);
 }
 
 bool
 IsParentProcess()
 {
   return XRE_GetProcessType() == GeckoProcessType_Default;
 }
 
-class MediaPlaybackRunnable : public nsRunnable
+class MediaPlaybackRunnable : public Runnable
 {
 public:
   MediaPlaybackRunnable(nsPIDOMWindowOuter* aWindow, bool aActive)
     : mWindow(aWindow)
     , mActive(aActive)
   {}
 
  NS_IMETHOD Run()
--- a/dom/base/ChromeUtils.cpp
+++ b/dom/base/ChromeUtils.cpp
@@ -69,32 +69,52 @@ ThreadSafeChromeUtils::Base64URLEncode(G
     const ArrayBufferView& view = aSource.GetAsArrayBufferView();
     view.ComputeLengthAndData();
     length = view.Length();
     data = view.Data();
   } else {
     MOZ_CRASH("Uninitialized union: expected buffer or view");
   }
 
-  nsresult rv = mozilla::Base64URLEncode(length, data, aOptions, aResult);
+  auto paddingPolicy = aOptions.mPad ? Base64URLEncodePaddingPolicy::Include :
+                                       Base64URLEncodePaddingPolicy::Omit;
+  nsresult rv = mozilla::Base64URLEncode(length, data, paddingPolicy, aResult);
   if (NS_WARN_IF(NS_FAILED(rv))) {
     aResult.Truncate();
     aRv.Throw(rv);
   }
 }
 
 /* static */ void
 ThreadSafeChromeUtils::Base64URLDecode(GlobalObject& aGlobal,
                                        const nsACString& aString,
                                        const Base64URLDecodeOptions& aOptions,
                                        JS::MutableHandle<JSObject*> aRetval,
                                        ErrorResult& aRv)
 {
+  Base64URLDecodePaddingPolicy paddingPolicy;
+  switch (aOptions.mPadding) {
+    case Base64URLDecodePadding::Require:
+      paddingPolicy = Base64URLDecodePaddingPolicy::Require;
+      break;
+
+    case Base64URLDecodePadding::Ignore:
+      paddingPolicy = Base64URLDecodePaddingPolicy::Ignore;
+      break;
+
+    case Base64URLDecodePadding::Reject:
+      paddingPolicy = Base64URLDecodePaddingPolicy::Reject;
+      break;
+
+    default:
+      aRv.Throw(NS_ERROR_INVALID_ARG);
+      return;
+  }
   FallibleTArray<uint8_t> data;
-  nsresult rv = mozilla::Base64URLDecode(aString, aOptions, data);
+  nsresult rv = mozilla::Base64URLDecode(aString, paddingPolicy, data);
   if (NS_WARN_IF(NS_FAILED(rv))) {
     aRv.Throw(rv);
     return;
   }
 
   JS::Rooted<JSObject*> buffer(aGlobal.Context(),
                                ArrayBuffer::Create(aGlobal.Context(),
                                                    data.Length(),
--- a/dom/base/Console.cpp
+++ b/dom/base/Console.cpp
@@ -307,17 +307,17 @@ public:
   {
     JS_ClearPendingException(mCx);
   }
 
 private:
   JSContext* mCx;
 };
 
-class ConsoleRunnable : public nsRunnable
+class ConsoleRunnable : public Runnable
                       , public WorkerFeature
                       , public StructuredCloneHolderBase
 {
 public:
   explicit ConsoleRunnable(Console* aConsole)
     : mWorkerPrivate(GetCurrentThreadWorkerPrivate())
     , mConsole(aConsole)
   {
--- a/dom/base/DOMRequest.cpp
+++ b/dom/base/DOMRequest.cpp
@@ -290,17 +290,17 @@ DOMRequestService::FireDetailedError(nsI
   NS_ENSURE_STATE(aRequest);
   nsCOMPtr<DOMError> err = do_QueryInterface(aError);
   NS_ENSURE_STATE(err);
   static_cast<DOMRequest*>(aRequest)->FireDetailedError(err);
 
   return NS_OK;
 }
 
-class FireSuccessAsyncTask : public nsRunnable
+class FireSuccessAsyncTask : public mozilla::Runnable
 {
 
   FireSuccessAsyncTask(DOMRequest* aRequest,
                        const JS::Value& aResult) :
     mReq(aRequest),
     mResult(nsContentUtils::RootingCxForThread(), aResult)
   {
   }
@@ -327,17 +327,17 @@ public:
     return NS_OK;
   }
 
 private:
   RefPtr<DOMRequest> mReq;
   JS::PersistentRooted<JS::Value> mResult;
 };
 
-class FireErrorAsyncTask : public nsRunnable
+class FireErrorAsyncTask : public mozilla::Runnable
 {
 public:
   FireErrorAsyncTask(DOMRequest* aRequest,
                      const nsAString& aError) :
     mReq(aRequest),
     mError(aError)
   {
   }
--- a/dom/base/Element.h
+++ b/dom/base/Element.h
@@ -1346,17 +1346,17 @@ private:
 
   nsIScrollableFrame* GetScrollFrame(nsIFrame **aStyledFrame = nullptr,
                                      bool aFlushLayout = true);
 
   // Data members
   EventStates mState;
 };
 
-class RemoveFromBindingManagerRunnable : public nsRunnable
+class RemoveFromBindingManagerRunnable : public mozilla::Runnable
 {
 public:
   RemoveFromBindingManagerRunnable(nsBindingManager* aManager,
                                    nsIContent* aContent,
                                    nsIDocument* aDoc);
 
   NS_IMETHOD Run() override;
 private:
--- a/dom/base/File.cpp
+++ b/dom/base/File.cpp
@@ -861,17 +861,17 @@ BlobImplFile::GetSize(ErrorResult& aRv)
     mLength = fileSize;
   }
 
   return mLength;
 }
 
 namespace {
 
-class GetTypeRunnable final : public nsRunnable
+class GetTypeRunnable final : public Runnable
 {
 public:
   GetTypeRunnable(WorkerPrivate* aWorkerPrivate,
                   nsIEventTarget* aSyncLoopTarget,
                   BlobImpl* aBlobImpl)
     : mWorkerPrivate(aWorkerPrivate)
     , mSyncLoopTarget(aSyncLoopTarget)
     , mBlobImpl(aBlobImpl)
--- a/dom/base/FragmentOrElement.cpp
+++ b/dom/base/FragmentOrElement.cpp
@@ -1232,17 +1232,17 @@ FragmentOrElement::FireNodeInserted(nsID
 }
 
 //----------------------------------------------------------------------
 
 // nsISupports implementation
 
 #define SUBTREE_UNBINDINGS_PER_RUNNABLE 500
 
-class ContentUnbinder : public nsRunnable
+class ContentUnbinder : public Runnable
 {
 public:
   ContentUnbinder()
   {
     mLast = this;
   }
 
   ~ContentUnbinder()
--- a/dom/base/ImageEncoder.cpp
+++ b/dom/base/ImageEncoder.cpp
@@ -21,17 +21,17 @@
 using namespace mozilla::gfx;
 
 namespace mozilla {
 namespace dom {
 
 // This class should be placed inside GetBRGADataSourceSurfaceSync(). However,
 // due to B2G ICS uses old complier (C++98/03) which forbids local class as
 // template parameter, we need to move this class outside.
-class SurfaceHelper : public nsRunnable {
+class SurfaceHelper : public Runnable {
 public:
   explicit SurfaceHelper(already_AddRefed<layers::Image> aImage) : mImage(aImage) {}
 
   // It retrieves a SourceSurface reference and convert color format on main
   // thread and passes DataSourceSurface to caller thread.
   NS_IMETHOD Run() {
     // It guarantees the reference will be released on main thread.
     nsCountedRef<nsMainThreadSourceSurfaceRef> surface;
@@ -130,17 +130,17 @@ private:
   uint64_t mImgSize;
   nsAutoString mType;
   void* mImgData;
   nsCOMPtr<nsIThread> mCreationThread;
   RefPtr<EncodeCompleteCallback> mEncodeCompleteCallback;
   bool mFailed;
 };
 
-class EncodingRunnable : public nsRunnable
+class EncodingRunnable : public Runnable
 {
   virtual ~EncodingRunnable() {}
 
 public:
   NS_DECL_ISUPPORTS_INHERITED
 
   EncodingRunnable(const nsAString& aType,
                    const nsAString& aOptions,
@@ -231,17 +231,17 @@ private:
   RefPtr<layers::Image> mImage;
   nsCOMPtr<imgIEncoder> mEncoder;
   RefPtr<EncodingCompleteEvent> mEncodingCompleteEvent;
   int32_t mFormat;
   const nsIntSize mSize;
   bool mUsingCustomOptions;
 };
 
-NS_IMPL_ISUPPORTS_INHERITED0(EncodingRunnable, nsRunnable);
+NS_IMPL_ISUPPORTS_INHERITED0(EncodingRunnable, Runnable);
 
 StaticRefPtr<nsIThreadPool> ImageEncoder::sThreadPool;
 
 /* static */
 nsresult
 ImageEncoder::ExtractData(nsAString& aType,
                           const nsAString& aOptions,
                           const nsIntSize aSize,
--- a/dom/base/ImportManager.cpp
+++ b/dom/base/ImportManager.cpp
@@ -373,17 +373,17 @@ ImportLoader::RemoveLinkElement(nsINode*
 {
   mLinks.RemoveElement(aNode);
 }
 
 // Events has to be fired with a script runner, so mImport can
 // be set on the link element before the load event is fired even
 // if ImportLoader::Get returns an already loaded import and we
 // fire the load event immediately on the new referring link element.
-class AsyncEvent : public nsRunnable {
+class AsyncEvent : public Runnable {
 public:
   AsyncEvent(nsINode* aNode, bool aSuccess)
     : mNode(aNode)
     , mSuccess(aSuccess)
   {
     MOZ_ASSERT(mNode);
   }
 
--- a/dom/base/PostMessageEvent.h
+++ b/dom/base/PostMessageEvent.h
@@ -19,17 +19,17 @@ class nsIPrincipal;
 
 namespace mozilla {
 namespace dom {
 
 /**
  * Class used to represent events generated by calls to Window.postMessage,
  * which asynchronously creates and dispatches events.
  */
-class PostMessageEvent final : public nsRunnable
+class PostMessageEvent final : public Runnable
                              , public StructuredCloneHolder
 {
 public:
   NS_DECL_NSIRUNNABLE
 
   PostMessageEvent(nsGlobalWindow* aSource,
                    const nsAString& aCallerOrigin,
                    nsGlobalWindow* aTargetWindow,
--- a/dom/base/WebSocket.cpp
+++ b/dom/base/WebSocket.cpp
@@ -384,17 +384,17 @@ WebSocketImpl::PrintErrorOnConsole(const
 
   // print the error message directly to the JS console
   rv = console->LogMessage(errorObject);
   NS_ENSURE_SUCCESS_VOID(rv);
 }
 
 namespace {
 
-class CancelWebSocketRunnable final : public nsRunnable
+class CancelWebSocketRunnable final : public Runnable
 {
 public:
   CancelWebSocketRunnable(nsIWebSocketChannel* aChannel, uint16_t aReasonCode,
                           const nsACString& aReasonString)
     : mChannel(aChannel)
     , mReasonCode(aReasonCode)
     , mReasonString(aReasonString)
   {}
@@ -432,17 +432,17 @@ public:
       mImpl->Disconnect();
     }
   }
 
 private:
   WebSocketImpl* mImpl;
 };
 
-class CloseConnectionRunnable final : public nsRunnable
+class CloseConnectionRunnable final : public Runnable
 {
 public:
   CloseConnectionRunnable(WebSocketImpl* aImpl,
                           uint16_t aReasonCode,
                           const nsACString& aReasonString)
     : mImpl(aImpl)
     , mReasonCode(aReasonCode)
     , mReasonString(aReasonString)
@@ -461,19 +461,19 @@ private:
 
 } // namespace
 
 nsresult
 WebSocketImpl::CloseConnection(uint16_t aReasonCode,
                                const nsACString& aReasonString)
 {
   if (!IsTargetThread()) {
-    RefPtr<nsRunnable> runnable =
+    nsCOMPtr<nsIRunnable> runnable =
       new CloseConnectionRunnable(this, aReasonCode, aReasonString);
-    return Dispatch(runnable, NS_DISPATCH_NORMAL);
+    return Dispatch(runnable.forget(), NS_DISPATCH_NORMAL);
   }
 
   AssertIsOnTargetThread();
 
   if (mDisconnectingOrDisconnected) {
     return NS_OK;
   }
 
--- a/dom/base/nsContentUtils.cpp
+++ b/dom/base/nsContentUtils.cpp
@@ -4728,17 +4728,17 @@ nsContentUtils::IsInSameAnonymousTree(co
   if (aNode->IsInShadowTree()) {
     return nodeAsContent->GetContainingShadow() ==
       aContent->GetContainingShadow();
   }
 
   return nodeAsContent->GetBindingParent() == aContent->GetBindingParent();
 }
 
-class AnonymousContentDestroyer : public nsRunnable {
+class AnonymousContentDestroyer : public Runnable {
 public:
   explicit AnonymousContentDestroyer(nsCOMPtr<nsIContent>* aContent) {
     mContent.swap(*aContent);
     mParent = mContent->GetParent();
     mDoc = mContent->OwnerDoc();
   }
   explicit AnonymousContentDestroyer(nsCOMPtr<Element>* aElement) {
     mContent = aElement->forget();
--- a/dom/base/nsDOMDataChannel.cpp
+++ b/dom/base/nsDOMDataChannel.cpp
@@ -18,16 +18,17 @@
 #include "mozilla/dom/MessageEventBinding.h"
 #include "mozilla/dom/ScriptSettings.h"
 
 #include "nsError.h"
 #include "nsAutoPtr.h"
 #include "nsContentUtils.h"
 #include "nsCycleCollectionParticipant.h"
 #include "nsIScriptObjectPrincipal.h"
+#include "nsProxyRelease.h"
 
 #include "DataChannel.h"
 #include "DataChannelLog.h"
 
 #undef LOG
 #define LOG(args) MOZ_LOG(mozilla::gDataChannelLog, mozilla::LogLevel::Debug, args)
 
 // Since we've moved the windows.h include down here, we have to explicitly
@@ -39,17 +40,17 @@
 using namespace mozilla;
 using namespace mozilla::dom;
 
 nsDOMDataChannel::~nsDOMDataChannel()
 {
   // Don't call us anymore!  Likely isn't an issue (or maybe just less of
   // one) once we block GC until all the (appropriate) onXxxx handlers
   // are dropped. (See WebRTC spec)
-  LOG(("Close()ing %p", mDataChannel.get()));
+  LOG(("%p: Close()ing %p", this, mDataChannel.get()));
   mDataChannel->SetListener(nullptr, nullptr);
   mDataChannel->Close();
 }
 
 /* virtual */ JSObject*
 nsDOMDataChannel::WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto)
 {
   return DataChannelBinding::Wrap(aCx, this, aGivenProto);
@@ -72,16 +73,18 @@ NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_
   NS_INTERFACE_MAP_ENTRY(nsIDOMDataChannel)
 NS_INTERFACE_MAP_END_INHERITING(DOMEventTargetHelper)
 
 nsDOMDataChannel::nsDOMDataChannel(already_AddRefed<mozilla::DataChannel>& aDataChannel,
                                    nsPIDOMWindowInner* aWindow)
   : DOMEventTargetHelper(aWindow)
   , mDataChannel(aDataChannel)
   , mBinaryType(DC_BINARY_TYPE_BLOB)
+  , mCheckMustKeepAlive(true)
+  , mSentClose(false)
 {
 }
 
 nsresult
 nsDOMDataChannel::Init(nsPIDOMWindowInner* aDOMWindow)
 {
   nsresult rv;
   nsAutoString urlParam;
@@ -258,16 +261,17 @@ nsDOMDataChannel::SetBinaryType(const ns
   }
   return NS_OK;
 }
 
 NS_IMETHODIMP
 nsDOMDataChannel::Close()
 {
   mDataChannel->Close();
+  UpdateMustKeepAlive();
   return NS_OK;
 }
 
 // All of the following is copy/pasted from WebSocket.cpp.
 void
 nsDOMDataChannel::Send(const nsAString& aData, ErrorResult& aRv)
 {
   NS_ConvertUTF16toUTF8 msgString(aData);
@@ -466,35 +470,145 @@ nsDOMDataChannel::OnChannelConnected(nsI
   LOG(("%p(%p): %s - Dispatching\n",this,(void*)mDataChannel,__FUNCTION__));
 
   return OnSimpleEvent(aContext, NS_LITERAL_STRING("open"));
 }
 
 nsresult
 nsDOMDataChannel::OnChannelClosed(nsISupports* aContext)
 {
-  LOG(("%p(%p): %s - Dispatching\n",this,(void*)mDataChannel,__FUNCTION__));
+  nsresult rv;
+  // so we don't have to worry if we're notified from different paths in
+  // the underlying code
+  if (!mSentClose) {
+    LOG(("%p(%p): %s - Dispatching\n",this,(void*)mDataChannel,__FUNCTION__));
 
-  return OnSimpleEvent(aContext, NS_LITERAL_STRING("close"));
+    rv = OnSimpleEvent(aContext, NS_LITERAL_STRING("close"));
+    // no more events can happen
+    mSentClose = true;
+  } else {
+    rv = NS_OK;
+  }
+  DontKeepAliveAnyMore();
+  return rv;
 }
 
 nsresult
 nsDOMDataChannel::OnBufferLow(nsISupports* aContext)
 {
   LOG(("%p(%p): %s - Dispatching\n",this,(void*)mDataChannel,__FUNCTION__));
 
   return OnSimpleEvent(aContext, NS_LITERAL_STRING("bufferedamountlow"));
 }
 
+nsresult
+nsDOMDataChannel::NotBuffered(nsISupports* aContext)
+{
+  // In the rare case that we held off GC to let the buffer drain
+  UpdateMustKeepAlive();
+  return NS_OK;
+}
+
 void
 nsDOMDataChannel::AppReady()
 {
   mDataChannel->AppReady();
 }
 
+//-----------------------------------------------------------------------------
+// Methods that keep alive the DataChannel object when:
+//   1. the object has registered event listeners that can be triggered
+//      ("strong event listeners");
+//   2. there are outgoing not sent messages.
+//-----------------------------------------------------------------------------
+
+void
+nsDOMDataChannel::UpdateMustKeepAlive()
+{
+  MOZ_ASSERT(NS_IsMainThread());
+
+  if (!mCheckMustKeepAlive) {
+    return;
+  }
+
+  bool shouldKeepAlive = false;
+  uint16_t readyState = mDataChannel->GetReadyState();
+
+  switch (readyState)
+  {
+    case DataChannel::CONNECTING:
+    case DataChannel::WAITING_TO_OPEN:
+    {
+      if (mListenerManager &&
+          (mListenerManager->HasListenersFor(nsGkAtoms::onopen) ||
+           mListenerManager->HasListenersFor(nsGkAtoms::onmessage) ||
+           mListenerManager->HasListenersFor(nsGkAtoms::onerror) ||
+           mListenerManager->HasListenersFor(nsGkAtoms::onbufferedamountlow) ||
+           mListenerManager->HasListenersFor(nsGkAtoms::onclose))) {
+        shouldKeepAlive = true;
+      }
+    }
+    break;
+
+    case DataChannel::OPEN:
+    case DataChannel::CLOSING:
+    {
+      if (mDataChannel->GetBufferedAmount() != 0 ||
+          (mListenerManager &&
+           (mListenerManager->HasListenersFor(nsGkAtoms::onmessage) ||
+            mListenerManager->HasListenersFor(nsGkAtoms::onerror) ||
+            mListenerManager->HasListenersFor(nsGkAtoms::onbufferedamountlow) ||
+            mListenerManager->HasListenersFor(nsGkAtoms::onclose)))) {
+        shouldKeepAlive = true;
+      }
+    }
+    break;
+
+    case DataChannel::CLOSED:
+    {
+      shouldKeepAlive = false;
+    }
+  }
+
+  if (mSelfRef && !shouldKeepAlive) {
+    // release our self-reference (safely) by putting it in an event (always)
+    NS_ReleaseOnMainThread(mSelfRef.forget(), true);
+  } else if (!mSelfRef && shouldKeepAlive) {
+    mSelfRef = this;
+  }
+}
+
+void
+nsDOMDataChannel::DontKeepAliveAnyMore()
+{
+  MOZ_ASSERT(NS_IsMainThread());
+
+  if (mSelfRef) {
+    // Since we're on MainThread, force an eventloop trip to avoid deleting ourselves.
+    NS_ReleaseOnMainThread(mSelfRef.forget(), true);
+  }
+
+  mCheckMustKeepAlive = false;
+}
+
+void
+nsDOMDataChannel::EventListenerAdded(nsIAtom* aType)
+{
+  MOZ_ASSERT(NS_IsMainThread());
+  UpdateMustKeepAlive();
+}
+
+void
+nsDOMDataChannel::EventListenerRemoved(nsIAtom* aType)
+{
+  MOZ_ASSERT(NS_IsMainThread());
+  UpdateMustKeepAlive();
+}
+
+
 /* static */
 nsresult
 NS_NewDOMDataChannel(already_AddRefed<mozilla::DataChannel>&& aDataChannel,
                      nsPIDOMWindowInner* aWindow,
                      nsIDOMDataChannel** aDomDataChannel)
 {
   RefPtr<nsDOMDataChannel> domdc =
     new nsDOMDataChannel(aDataChannel, aWindow);
--- a/dom/base/nsDOMDataChannel.h
+++ b/dom/base/nsDOMDataChannel.h
@@ -37,16 +37,20 @@ public:
   NS_DECL_ISUPPORTS_INHERITED
   NS_DECL_NSIDOMDATACHANNEL
 
   NS_REALLY_FORWARD_NSIDOMEVENTTARGET(mozilla::DOMEventTargetHelper)
 
   NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsDOMDataChannel,
                                            mozilla::DOMEventTargetHelper)
 
+  // EventTarget
+  virtual void EventListenerAdded(nsIAtom* aType) override;
+  virtual void EventListenerRemoved(nsIAtom* aType) override;
+
   virtual JSObject* WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto)
     override;
   nsPIDOMWindowInner* GetParentObject() const
   {
     return GetOwner();
   }
 
   // WebIDL
@@ -98,29 +102,44 @@ public:
   OnChannelConnected(nsISupports* aContext) override;
 
   virtual nsresult
   OnChannelClosed(nsISupports* aContext) override;
 
   virtual nsresult
   OnBufferLow(nsISupports* aContext) override;
 
+  virtual nsresult
+  NotBuffered(nsISupports* aContext) override;
+
   virtual void
   AppReady();
 
+  // if there are "strong event listeners" or outgoing not sent messages
+  // then this method keeps the object alive when js doesn't have strong
+  // references to it.
+  void UpdateMustKeepAlive();
+  // ATTENTION, when calling this method the object can be released
+  // (and possibly collected).
+  void DontKeepAliveAnyMore();
+
 protected:
   ~nsDOMDataChannel();
 
 private:
   void Send(nsIInputStream* aMsgStream, const nsACString& aMsgString,
             uint32_t aMsgLength, bool aIsBinary, mozilla::ErrorResult& aRv);
 
+  // to keep us alive while we have listeners
+  RefPtr<nsDOMDataChannel> mSelfRef;
   // Owning reference
   RefPtr<mozilla::DataChannel> mDataChannel;
   nsString  mOrigin;
   enum DataChannelBinaryType {
     DC_BINARY_TYPE_ARRAYBUFFER,
     DC_BINARY_TYPE_BLOB,
   };
   DataChannelBinaryType mBinaryType;
+  bool mCheckMustKeepAlive;
+  bool mSentClose;
 };
 
 #endif // nsDOMDataChannel_h
--- a/dom/base/nsDOMMutationObserver.cpp
+++ b/dom/base/nsDOMMutationObserver.cpp
@@ -850,17 +850,17 @@ nsDOMMutationObserver::HandleMutation()
       current.swap(next);
     }
   }
   ClearPendingRecords();
 
   mCallback->Call(this, mutations, *this);
 }
 
-class AsyncMutationHandler : public nsRunnable
+class AsyncMutationHandler : public mozilla::Runnable
 {
 public:
   NS_IMETHOD Run()
   {
     nsDOMMutationObserver::HandleMutations();
     return NS_OK;
   }
 };
--- a/dom/base/nsDOMWindowUtils.cpp
+++ b/dom/base/nsDOMWindowUtils.cpp
@@ -375,17 +375,19 @@ nsDOMWindowUtils::SetDisplayPortForEleme
     if (displayport.IsEmpty() &&
         rootFrame == nsLayoutUtils::GetDisplayRootFrame(rootFrame)) {
       nsCOMPtr<nsIWidget> widget = GetWidget();
       if (widget) {
         bool isRetainingManager;
         LayerManager* manager = widget->GetLayerManager(&isRetainingManager);
         if (isRetainingManager) {
           manager->BeginTransaction();
-          nsLayoutUtils::PaintFrame(nullptr, rootFrame, nsRegion(), NS_RGB(255, 255, 255),
+          nsLayoutUtils::PaintFrame(nullptr, rootFrame, nsRegion(),
+                                    NS_RGB(255, 255, 255),
+                                    nsDisplayListBuilderMode::PAINTING,
                                     nsLayoutUtils::PAINT_WIDGET_LAYERS |
                                     nsLayoutUtils::PAINT_EXISTING_TRANSACTION);
         }
       }
     }
   }
 
   return NS_OK;
--- a/dom/base/nsDocElementCreatedNotificationRunner.h
+++ b/dom/base/nsDocElementCreatedNotificationRunner.h
@@ -9,17 +9,17 @@
 
 #include "mozilla/Attributes.h"
 #include "nsThreadUtils.h" /* nsRunnable */
 
 #include "nsContentSink.h"
 #include "nsCOMPtr.h"
 #include "nsIDocument.h"
 
-class nsDocElementCreatedNotificationRunner : public nsRunnable
+class nsDocElementCreatedNotificationRunner : public mozilla::Runnable
 {
 public:
   explicit nsDocElementCreatedNotificationRunner(nsIDocument* aDoc)
     : mDoc(aDoc)
   {
   }
 
   NS_IMETHOD Run() override
--- a/dom/base/nsDocument.cpp
+++ b/dom/base/nsDocument.cpp
@@ -1355,17 +1355,17 @@ nsIDocument::SelectorCache::SelectorCach
 void nsIDocument::SelectorCache::CacheList(const nsAString& aSelector,
                                            nsCSSSelectorList* aSelectorList)
 {
   SelectorCacheKey* key = new SelectorCacheKey(aSelector);
   mTable.Put(key->mKey, aSelectorList);
   AddObject(key);
 }
 
-class nsIDocument::SelectorCacheKeyDeleter final : public nsRunnable
+class nsIDocument::SelectorCacheKeyDeleter final : public Runnable
 {
 public:
   explicit SelectorCacheKeyDeleter(SelectorCacheKey* aToDelete)
     : mSelector(aToDelete)
   {
     MOZ_COUNT_CTOR(SelectorCacheKeyDeleter);
   }
 
@@ -9142,17 +9142,17 @@ nsDocument::UnblockOnload(bool aFireSync
                                  NS_LITERAL_STRING("MozSVGAsImageDocumentLoad"),
                                  false,
                                  false);
       asyncDispatcher->PostDOMEvent();
     }
   }
 }
 
-class nsUnblockOnloadEvent : public nsRunnable {
+class nsUnblockOnloadEvent : public Runnable {
 public:
   explicit nsUnblockOnloadEvent(nsDocument* aDoc) : mDoc(aDoc) {}
   NS_IMETHOD Run() {
     mDoc->DoUnblockOnload();
     return NS_OK;
   }
 private:
   RefPtr<nsDocument> mDoc;
@@ -10016,17 +10016,17 @@ nsDocument::LoadChromeSheetSync(nsIURI* 
                                 mozilla::StyleSheetHandle::RefPtr* aSheet)
 {
   css::SheetParsingMode mode =
     isAgentSheet ? css::eAgentSheetFeatures
                  : css::eAuthorSheetFeatures;
   return CSSLoader()->LoadSheetSync(uri, mode, isAgentSheet, aSheet);
 }
 
-class nsDelayedEventDispatcher : public nsRunnable
+class nsDelayedEventDispatcher : public Runnable
 {
 public:
   explicit nsDelayedEventDispatcher(nsTArray<nsCOMPtr<nsIDocument>>& aDocuments)
   {
     mDocuments.SwapElements(aDocuments);
   }
   virtual ~nsDelayedEventDispatcher() {}
 
@@ -11205,17 +11205,17 @@ AskWindowToExitFullscreen(nsIDocument* a
       /* DefaultAction */ nullptr);
   } else {
     if (nsPIDOMWindowOuter* win = aDoc->GetWindow()) {
       win->SetFullscreenInternal(FullscreenReason::ForFullscreenAPI, false);
     }
   }
 }
 
-class nsCallExitFullscreen : public nsRunnable
+class nsCallExitFullscreen : public Runnable
 {
 public:
   explicit nsCallExitFullscreen(nsIDocument* aDoc)
     : mDoc(aDoc) {}
 
   NS_IMETHOD Run() override final
   {
     if (!mDoc) {
@@ -11279,17 +11279,17 @@ ResetFullScreen(nsIDocument* aDocument, 
     aDocument->EnumerateSubDocuments(ResetFullScreen, aData);
   }
   return true;
 }
 
 // Since nsIDocument::ExitFullscreenInDocTree() could be called from
 // Element::UnbindFromTree() where it is not safe to synchronously run
 // script. This runnable is the script part of that function.
-class ExitFullscreenScriptRunnable : public nsRunnable
+class ExitFullscreenScriptRunnable : public Runnable
 {
 public:
   explicit ExitFullscreenScriptRunnable(nsCOMArray<nsIDocument>&& aDocuments)
     : mDocuments(Move(aDocuments)) { }
 
   NS_IMETHOD Run() override
   {
     // Dispatch MozDOMFullscreen:Exited to the last document in
@@ -11473,17 +11473,17 @@ nsDocument::RestorePreviousFullScreenSta
     // cross origin, dispatch an event to chrome so it knows to show
     // the warning UI.
     DispatchCustomEventWithFlush(
       newFullscreenDoc, NS_LITERAL_STRING("MozDOMFullscreen:NewOrigin"),
       /* Bubbles */ true, /* ChromeOnly */ true);
   }
 }
 
-class nsCallRequestFullScreen : public nsRunnable
+class nsCallRequestFullScreen : public Runnable
 {
 public:
   explicit nsCallRequestFullScreen(UniquePtr<FullscreenRequest>&& aRequest)
     : mRequest(Move(aRequest)) { }
 
   NS_IMETHOD Run()
   {
     mRequest->GetDocument()->RequestFullScreen(Move(mRequest));
@@ -11720,18 +11720,18 @@ HasFullScreenSubDocument(nsIDocument* aD
 // in the given document. Returns a static string indicates the reason
 // why it is not enabled otherwise.
 static const char*
 GetFullscreenError(nsIDocument* aDoc, bool aCallerIsChrome)
 {
   if (nsContentUtils::IsFullScreenApiEnabled() && aCallerIsChrome) {
     // Chrome code can always use the full-screen API, provided it's not
     // explicitly disabled. Note IsCallerChrome() returns true when running
-    // in an nsRunnable, so don't use GetMozFullScreenEnabled() from an
-    // nsRunnable!
+    // in a Runnable, so don't use GetMozFullScreenEnabled() from a
+    // Runnable!
     return nullptr;
   }
 
   if (!nsContentUtils::IsFullScreenApiEnabled()) {
     return "FullscreenDeniedDisabled";
   }
   if (!aDoc->IsVisible()) {
     return "FullscreenDeniedHidden";
@@ -12246,17 +12246,17 @@ DispatchPointerLockError(nsIDocument* aT
   asyncDispatcher->PostDOMEvent();
 }
 
 static const uint8_t kPointerLockRequestLimit = 2;
 
 class nsPointerLockPermissionRequest;
 mozilla::StaticRefPtr<nsPointerLockPermissionRequest> gPendingPointerLockRequest;
 
-class nsPointerLockPermissionRequest : public nsRunnable,
+class nsPointerLockPermissionRequest : public Runnable,
                                        public nsIContentPermissionRequest
 {
 public:
   nsPointerLockPermissionRequest(Element* aElement, bool aUserInputOrChromeCaller)
   : mElement(do_GetWeakReference(aElement)),
     mDocument(do_GetWeakReference(aElement->OwnerDoc())),
     mUserInputOrChromeCaller(aUserInputOrChromeCaller)
   {
@@ -12321,17 +12321,17 @@ public:
   bool mUserInputOrChromeCaller;
 
 protected:
   virtual ~nsPointerLockPermissionRequest() {}
   nsCOMPtr<nsIContentPermissionRequester> mRequester;
 };
 
 NS_IMPL_ISUPPORTS_INHERITED(nsPointerLockPermissionRequest,
-                            nsRunnable,
+                            Runnable,
                             nsIContentPermissionRequest)
 
 NS_IMETHODIMP
 nsPointerLockPermissionRequest::GetTypes(nsIArray** aTypes)
 {
   nsTArray<nsString> emptyOptions;
   return nsContentPermissionUtils::CreatePermissionArray(NS_LITERAL_CSTRING("pointerLock"),
                                                          NS_LITERAL_CSTRING("unused"),
--- a/dom/base/nsFocusManager.cpp
+++ b/dom/base/nsFocusManager.cpp
@@ -1953,17 +1953,17 @@ nsFocusManager::Focus(nsPIDOMWindowOuter
   if (mFocusedContent == aContent)
     UpdateCaret(aFocusChanged && !(aFlags & FLAG_BYMOUSE), aIsNewDocument,
                 mFocusedContent);
 
   if (clearFirstFocusEvent)
     mFirstFocusEvent = nullptr;
 }
 
-class FocusBlurEvent : public nsRunnable
+class FocusBlurEvent : public Runnable
 {
 public:
   FocusBlurEvent(nsISupports* aTarget, EventMessage aEventMessage,
                  nsPresContext* aContext, bool aWindowRaised,
                  bool aIsRefocus, EventTarget* aRelatedTarget)
     : mTarget(aTarget)
     , mContext(aContext)
     , mEventMessage(aEventMessage)
@@ -3448,17 +3448,17 @@ nsFocusManager::GetFocusInSelection(nsPI
       if (selectionNode)
         break;
       selectionNode = testNode;
     } while (true);
   }
   while (selectionNode && selectionNode != endSelectionNode);
 }
 
-class PointerUnlocker : public nsRunnable
+class PointerUnlocker : public Runnable
 {
 public:
   PointerUnlocker()
   {
     MOZ_ASSERT(!PointerUnlocker::sActiveUnlocker);
     PointerUnlocker::sActiveUnlocker = this;
   }
 
--- a/dom/base/nsFrameLoader.cpp
+++ b/dom/base/nsFrameLoader.cpp
@@ -1400,17 +1400,17 @@ nsFrameLoader::SwapWithOtherLoader(nsFra
 
 NS_IMETHODIMP
 nsFrameLoader::Destroy()
 {
   StartDestroy();
   return NS_OK;
 }
 
-class nsFrameLoaderDestroyRunnable : public nsRunnable
+class nsFrameLoaderDestroyRunnable : public Runnable
 {
   enum DestroyPhase
   {
     // See the implementation of Run for an explanation of these phases.
     eDestroyDocShell,
     eWaitForUnloadMessage,
     eDestroyComplete
   };
@@ -2576,17 +2576,17 @@ nsFrameLoader::DoLoadMessageManagerScrip
     static_cast<nsInProcessTabChildGlobal*>(GetTabChildGlobalAsEventTarget());
   if (tabChild) {
     tabChild->LoadFrameScript(aURL, aRunInGlobalScope);
   }
   return true;
 }
 
 class nsAsyncMessageToChild : public nsSameProcessAsyncMessageBase,
-                              public nsRunnable
+                              public Runnable
 {
 public:
   nsAsyncMessageToChild(JSContext* aCx, JS::Handle<JSObject*> aCpows, nsFrameLoader* aFrameLoader)
     : nsSameProcessAsyncMessageBase(aCx, aCpows)
     , mFrameLoader(aFrameLoader)
   {
   }
 
--- a/dom/base/nsFrameMessageManager.cpp
+++ b/dom/base/nsFrameMessageManager.cpp
@@ -1885,17 +1885,17 @@ nsMessageManagerScriptExecutor::MarkScop
 
 NS_IMPL_ISUPPORTS(nsScriptCacheCleaner, nsIObserver)
 
 nsFrameMessageManager* nsFrameMessageManager::sChildProcessManager = nullptr;
 nsFrameMessageManager* nsFrameMessageManager::sParentProcessManager = nullptr;
 nsFrameMessageManager* nsFrameMessageManager::sSameProcessParentManager = nullptr;
 
 class nsAsyncMessageToSameProcessChild : public nsSameProcessAsyncMessageBase,
-                                         public nsRunnable
+                                         public Runnable
 {
 public:
   nsAsyncMessageToSameProcessChild(JSContext* aCx, JS::Handle<JSObject*> aCpows)
     : nsSameProcessAsyncMessageBase(aCx, aCpows)
   { }
   NS_IMETHOD Run()
   {
     nsFrameMessageManager* ppm = nsFrameMessageManager::GetChildProcessManager();
--- a/dom/base/nsFrameMessageManager.h
+++ b/dom/base/nsFrameMessageManager.h
@@ -312,17 +312,17 @@ private:
   nsresult AssertProcessInternal(ProcessCheckerType aType,
                                  const nsAString& aCapability,
                                  bool* aValid);
 };
 
 /* A helper class for taking care of many details for async message sending
    within a single process.  Intended to be used like so:
 
-   class MyAsyncMessage : public nsSameProcessAsyncMessageBase, public nsRunnable
+   class MyAsyncMessage : public nsSameProcessAsyncMessageBase, public Runnable
    {
      NS_IMETHOD Run() {
        ReceiveMessage(..., ...);
        return NS_OK;
      }
    };
 
 
--- a/dom/base/nsGlobalWindow.cpp
+++ b/dom/base/nsGlobalWindow.cpp
@@ -5907,17 +5907,17 @@ GetFullscreenTransitionDuration(bool aEn
     "full-screen-api.transition-duration.leave";
   nsAdoptingCString prefValue = Preferences::GetCString(pref);
   if (!prefValue.IsEmpty()) {
     sscanf(prefValue.get(), "%hu%hu",
            &aDuration->mFadeIn, &aDuration->mFadeOut);
   }
 }
 
-class FullscreenTransitionTask : public nsRunnable
+class FullscreenTransitionTask : public Runnable
 {
 public:
   FullscreenTransitionTask(const FullscreenTransitionDuration& aDuration,
                            nsGlobalWindow* aWindow, bool aFullscreen,
                            nsIWidget* aWidget, nsIScreen* aScreen,
                            nsISupports* aTransitionData)
     : mWindow(aWindow)
     , mWidget(aWidget)
@@ -8143,17 +8143,17 @@ nsGlobalWindow::PostMessageMoz(JSContext
       aError.Throw(NS_ERROR_OUT_OF_MEMORY);
       return;
     }
   }
 
   PostMessageMoz(aCx, aMessage, aTargetOrigin, transferArray, aError);
 }
 
-class nsCloseEvent : public nsRunnable {
+class nsCloseEvent : public Runnable {
 
   RefPtr<nsGlobalWindow> mWindow;
   bool mIndirect;
 
   nsCloseEvent(nsGlobalWindow *aWindow, bool aIndirect)
     : mWindow(aWindow)
     , mIndirect(aIndirect)
   {}
@@ -8524,17 +8524,17 @@ nsGlobalWindow::RunPendingTimeoutsRecurs
     }
 
     auto* childWin = nsGlobalWindow::Cast(child);
 
     RunPendingTimeoutsRecursive(aTopWindow, childWin);
   }
 }
 
-class nsPendingTimeoutRunner : public nsRunnable
+class nsPendingTimeoutRunner : public Runnable
 {
 public:
   explicit nsPendingTimeoutRunner(nsGlobalWindow* aWindow)
     : mWindow(aWindow)
   {
     NS_ASSERTION(mWindow, "mWindow is null.");
   }
 
@@ -8624,17 +8624,17 @@ struct BrowserCompartmentMatcher : publi
   virtual bool match(JSCompartment* c) const override
   {
     nsCOMPtr<nsIPrincipal> pc = nsJSPrincipals::get(JS_GetCompartmentPrincipals(c));
     return nsContentUtils::IsSystemOrExpandedPrincipal(pc);
   }
 };
 
 
-class WindowDestroyedEvent : public nsRunnable
+class WindowDestroyedEvent : public Runnable
 {
 public:
   WindowDestroyedEvent(nsIDOMWindow* aWindow, uint64_t aID,
                        const char* aTopic) :
     mID(aID), mTopic(aTopic)
   {
     mWindow = do_GetWeakReference(aWindow);
   }
@@ -9055,17 +9055,17 @@ nsGlobalWindow::ShowModalDialog(JSContex
     aError = nsContentUtils::XPConnect()->VariantToJS(aCx,
                                                       FastGetGlobalJSObject(),
                                                       retVal, aRetval);
   } else {
     aRetval.setNull();
   }
 }
 
-class ChildCommandDispatcher : public nsRunnable
+class ChildCommandDispatcher : public Runnable
 {
 public:
   ChildCommandDispatcher(nsGlobalWindow* aWindow,
                          nsITabChild* aTabChild,
                          const nsAString& aAction)
   : mWindow(aWindow), mTabChild(aTabChild), mAction(aAction) {}
 
   NS_IMETHOD Run()
@@ -9085,17 +9085,17 @@ public:
   }
 
 private:
   RefPtr<nsGlobalWindow>             mWindow;
   nsCOMPtr<nsITabChild>                mTabChild;
   nsString                             mAction;
 };
 
-class CommandDispatcher : public nsRunnable
+class CommandDispatcher : public Runnable
 {
 public:
   CommandDispatcher(nsIDOMXULCommandDispatcher* aDispatcher,
                     const nsAString& aAction)
   : mDispatcher(aDispatcher), mAction(aAction) {}
 
   NS_IMETHOD Run()
   {
@@ -9885,17 +9885,17 @@ nsGlobalWindow::PageHidden()
   nsIFocusManager* fm = nsFocusManager::GetFocusManager();
   if (fm) {
     fm->WindowHidden(GetOuterWindow());
   }
 
   mNeedsFocus = true;
 }
 
-class HashchangeCallback : public nsRunnable
+class HashchangeCallback : public Runnable
 {
 public:
   HashchangeCallback(const nsAString &aOldURL,
                      const nsAString &aNewURL,
                      nsGlobalWindow* aWindow)
     : mWindow(aWindow)
   {
     MOZ_ASSERT(mWindow);
@@ -10492,17 +10492,17 @@ nsGlobalWindow::FireOfflineStatusEventIf
     Element* documentElement = mDoc->GetDocumentElement();
     if (documentElement) {
       eventTarget = documentElement;
     }
   }
   nsContentUtils::DispatchTrustedEvent(mDoc, eventTarget, name, true, false);
 }
 
-class NotifyIdleObserverRunnable : public nsRunnable
+class NotifyIdleObserverRunnable : public Runnable
 {
 public:
   NotifyIdleObserverRunnable(nsIIdleObserver* aIdleObserver,
                              uint32_t aTimeInS,
                              bool aCallOnidle,
                              nsGlobalWindow* aIdleWindow)
     : mIdleObserver(aIdleObserver), mTimeInS(aTimeInS), mIdleWindow(aIdleWindow),
       mCallOnidle(aCallOnidle)
--- a/dom/base/nsIGlobalObject.cpp
+++ b/dom/base/nsIGlobalObject.cpp
@@ -34,17 +34,17 @@ nsIGlobalObject::RegisterHostObjectURI(c
 void
 nsIGlobalObject::UnregisterHostObjectURI(const nsACString& aURI)
 {
   mHostObjectURIs.RemoveElement(aURI);
 }
 
 namespace {
 
-class UnlinkHostObjectURIsRunnable final : public nsRunnable
+class UnlinkHostObjectURIsRunnable final : public mozilla::Runnable
 {
 public:
   explicit UnlinkHostObjectURIsRunnable(nsTArray<nsCString>& aURIs)
   {
     mURIs.SwapElements(aURIs);
   }
 
   NS_IMETHOD Run() override
--- a/dom/base/nsInProcessTabChildGlobal.cpp
+++ b/dom/base/nsInProcessTabChildGlobal.cpp
@@ -299,17 +299,17 @@ nsInProcessTabChildGlobal::InitTabChildG
     id.AppendLiteral("?ownedBy=");
     id.Append(u);
   }
   nsISupports* scopeSupports = NS_ISUPPORTS_CAST(EventTarget*, this);
   NS_ENSURE_STATE(InitChildGlobalInternal(scopeSupports, id));
   return NS_OK;
 }
 
-class nsAsyncScriptLoad : public nsRunnable
+class nsAsyncScriptLoad : public Runnable
 {
 public:
     nsAsyncScriptLoad(nsInProcessTabChildGlobal* aTabChild, const nsAString& aURL,
                       bool aRunInGlobalScope)
       : mTabChild(aTabChild), mURL(aURL), mRunInGlobalScope(aRunInGlobalScope) {}
 
   NS_IMETHOD Run()
   {
--- a/dom/base/nsJSEnvironment.cpp
+++ b/dom/base/nsJSEnvironment.cpp
@@ -414,17 +414,17 @@ NS_HandleScriptError(nsIScriptGlobalObje
                                         aStatus);
       called = true;
     }
     --errorDepth;
   }
   return called;
 }
 
-class ScriptErrorEvent : public nsRunnable
+class ScriptErrorEvent : public Runnable
 {
 public:
   ScriptErrorEvent(nsPIDOMWindowInner* aWindow,
                    JSRuntime* aRuntime,
                    xpc::ErrorReport* aReport,
                    JS::Handle<JS::Value> aError)
     : mWindow(aWindow)
     , mReport(aReport)
@@ -2175,17 +2175,17 @@ nsJSContext::KillICCTimer()
   sCCLockedOutTime = 0;
 
   if (sICCTimer) {
     sICCTimer->Cancel();
     NS_RELEASE(sICCTimer);
   }
 }
 
-class NotifyGCEndRunnable : public nsRunnable
+class NotifyGCEndRunnable : public Runnable
 {
   nsString mMessage;
 
 public:
   explicit NotifyGCEndRunnable(const nsString& aMessage) : mMessage(aMessage) {}
 
   NS_DECL_NSIRUNNABLE
 };
--- a/dom/base/nsJSEnvironment.h
+++ b/dom/base/nsJSEnvironment.h
@@ -181,17 +181,17 @@ void ShutdownJSEnvironment();
 
 // Get the NameSpaceManager, creating if necessary
 nsScriptNameSpaceManager* GetNameSpaceManager();
 
 // Peek the NameSpaceManager, without creating it.
 nsScriptNameSpaceManager* PeekNameSpaceManager();
 
 // Runnable that's used to do async error reporting
-class AsyncErrorReporter final : public nsRunnable
+class AsyncErrorReporter final : public mozilla::Runnable
 {
 public:
   // aWindow may be null if this error report is not associated with a window
   explicit AsyncErrorReporter(xpc::ErrorReport* aReport)
     : mReport(aReport)
   {}
 
   NS_IMETHOD Run() override
--- a/dom/base/nsObjectLoadingContent.cpp
+++ b/dom/base/nsObjectLoadingContent.cpp
@@ -135,17 +135,17 @@ InActiveDocument(nsIContent *aContent)
   nsIDocument *doc = aContent->OwnerDoc();
   return (doc && doc->IsActive());
 }
 
 ///
 /// Runnables and helper classes
 ///
 
-class nsAsyncInstantiateEvent : public nsRunnable {
+class nsAsyncInstantiateEvent : public Runnable {
 public:
   explicit nsAsyncInstantiateEvent(nsObjectLoadingContent* aContent)
   : mContent(aContent) {}
 
   ~nsAsyncInstantiateEvent() {}
 
   NS_IMETHOD Run();
 
@@ -168,17 +168,17 @@ nsAsyncInstantiateEvent::Run()
 
   return objLC->SyncStartPluginInstance();
 }
 
 // Checks to see if the content for a plugin instance should be unloaded
 // (outside an active document) or stopped (in a document but unrendered). This
 // is used to allow scripts to move a plugin around the document hierarchy
 // without re-instantiating it.
-class CheckPluginStopEvent : public nsRunnable {
+class CheckPluginStopEvent : public Runnable {
 public:
   explicit CheckPluginStopEvent(nsObjectLoadingContent* aContent)
   : mContent(aContent) {}
 
   ~CheckPluginStopEvent() {}
 
   NS_IMETHOD Run();
 
@@ -243,17 +243,17 @@ CheckPluginStopEvent::Run()
   objLC->StopPluginInstance();
 
   return NS_OK;
 }
 
 /**
  * Helper task for firing simple events
  */
-class nsSimplePluginEvent : public nsRunnable {
+class nsSimplePluginEvent : public Runnable {
 public:
   nsSimplePluginEvent(nsIContent* aTarget, const nsAString &aEvent)
     : mTarget(aTarget)
     , mDocument(aTarget->GetComposedDoc())
     , mEvent(aEvent)
   {
     MOZ_ASSERT(aTarget && mDocument);
   }
@@ -296,17 +296,17 @@ nsSimplePluginEvent::Run()
                                          mEvent, true, true);
   }
   return NS_OK;
 }
 
 /**
  * A task for firing PluginCrashed DOM Events.
  */
-class nsPluginCrashedEvent : public nsRunnable {
+class nsPluginCrashedEvent : public Runnable {
 public:
   nsCOMPtr<nsIContent> mContent;
   nsString mPluginDumpID;
   nsString mBrowserDumpID;
   nsString mPluginName;
   nsString mPluginFilename;
   bool mSubmittedCrashReport;
 
@@ -355,46 +355,46 @@ nsPluginCrashedEvent::Run()
 
   event->SetTrusted(true);
   event->WidgetEventPtr()->mFlags.mOnlyChromeDispatch = true;
 
   EventDispatcher::DispatchDOMEvent(mContent, nullptr, event, nullptr, nullptr);
   return NS_OK;
 }
 
-class nsStopPluginRunnable : public nsRunnable, public nsITimerCallback
+class nsStopPluginRunnable : public Runnable, public nsITimerCallback
 {
 public:
   NS_DECL_ISUPPORTS_INHERITED
 
   nsStopPluginRunnable(nsPluginInstanceOwner* aInstanceOwner,
                        nsObjectLoadingContent* aContent)
     : mInstanceOwner(aInstanceOwner)
     , mContent(aContent)
   {
     NS_ASSERTION(aInstanceOwner, "need an owner");
     NS_ASSERTION(aContent, "need a nsObjectLoadingContent");
   }
 
-  // nsRunnable
+  // Runnable
   NS_IMETHOD Run() override;
 
   // nsITimerCallback
   NS_IMETHOD Notify(nsITimer* timer) override;
 
 protected:
   virtual ~nsStopPluginRunnable() {}
 
 private:
   nsCOMPtr<nsITimer> mTimer;
   RefPtr<nsPluginInstanceOwner> mInstanceOwner;
   nsCOMPtr<nsIObjectLoadingContent> mContent;
 };
 
-NS_IMPL_ISUPPORTS_INHERITED(nsStopPluginRunnable, nsRunnable, nsITimerCallback)
+NS_IMPL_ISUPPORTS_INHERITED(nsStopPluginRunnable, Runnable, nsITimerCallback)
 
 NS_IMETHODIMP
 nsStopPluginRunnable::Notify(nsITimer *aTimer)
 {
   return Run();
 }
 
 NS_IMETHODIMP
--- a/dom/base/nsReferencedElement.cpp
+++ b/dom/base/nsReferencedElement.cpp
@@ -210,17 +210,17 @@ nsReferencedElement::Observe(Element* aO
   if (!keepTracking) {
     p->mWatchDocument = nullptr;
     p->mWatchID = nullptr;
   }
   return keepTracking;
 }
 
 NS_IMPL_ISUPPORTS_INHERITED0(nsReferencedElement::ChangeNotification,
-                             nsRunnable)
+                             mozilla::Runnable)
 
 NS_IMPL_ISUPPORTS(nsReferencedElement::DocumentLoadNotification,
                   nsIObserver)
 
 NS_IMETHODIMP
 nsReferencedElement::DocumentLoadNotification::Observe(nsISupports* aSubject,
                                                        const char* aTopic,
                                                        const char16_t* aData)
--- a/dom/base/nsReferencedElement.h
+++ b/dom/base/nsReferencedElement.h
@@ -118,17 +118,17 @@ private:
     explicit Notification(nsReferencedElement* aTarget)
       : mTarget(aTarget)
     {
       NS_PRECONDITION(aTarget, "Must have a target");
     }
     nsReferencedElement* mTarget;
   };
 
-  class ChangeNotification : public nsRunnable,
+  class ChangeNotification : public mozilla::Runnable,
                              public Notification
   {
   public:
     ChangeNotification(nsReferencedElement* aTarget,
                        Element* aFrom, Element* aTo)
       : Notification(aTarget), mFrom(aFrom), mTo(aTo)
     {}
 
--- a/dom/base/nsScriptLoader.cpp
+++ b/dom/base/nsScriptLoader.cpp
@@ -368,17 +368,17 @@ bool
 nsScriptLoader::PreloadURIComparator::Equals(const PreloadInfo &aPi,
                                              nsIURI * const &aURI) const
 {
   bool same;
   return NS_SUCCEEDED(aPi.mRequest->mURI->Equals(aURI, &same)) &&
          same;
 }
 
-class nsScriptRequestProcessor : public nsRunnable
+class nsScriptRequestProcessor : public Runnable
 {
 private:
   RefPtr<nsScriptLoader> mLoader;
   RefPtr<nsScriptLoadRequest> mRequest;
 public:
   nsScriptRequestProcessor(nsScriptLoader* aLoader,
                            nsScriptLoadRequest* aRequest)
     : mLoader(aLoader)
@@ -723,17 +723,17 @@ nsScriptLoader::ProcessScriptElement(nsI
   // is on the call stack.
   NS_ASSERTION(nsContentUtils::IsSafeToRunScript(),
       "Not safe to run a parser-inserted script?");
   return ProcessRequest(request) == NS_ERROR_HTMLPARSER_BLOCK;
 }
 
 namespace {
 
-class NotifyOffThreadScriptLoadCompletedRunnable : public nsRunnable
+class NotifyOffThreadScriptLoadCompletedRunnable : public Runnable
 {
   RefPtr<nsScriptLoadRequest> mRequest;
   RefPtr<nsScriptLoader> mLoader;
   void *mToken;
 
 public:
   NotifyOffThreadScriptLoadCompletedRunnable(nsScriptLoadRequest* aRequest,
                                              nsScriptLoader* aLoader)
--- a/dom/base/nsXMLHttpRequest.cpp
+++ b/dom/base/nsXMLHttpRequest.cpp
@@ -146,17 +146,17 @@ using namespace mozilla::dom;
     nsCString tmp;                                                              \
     _name(tmp);                                                                 \
     aOut = tmp;                                                                 \
     return NS_OK;                                                               \
   }
 
 NS_IMPL_ISUPPORTS(nsXHRParseEndListener, nsIDOMEventListener)
 
-class nsResumeTimeoutsEvent : public nsRunnable
+class nsResumeTimeoutsEvent : public Runnable
 {
 public:
   explicit nsResumeTimeoutsEvent(nsPIDOMWindowInner* aWindow) : mWindow(aWindow) {}
 
   NS_IMETHOD Run()
   {
     mWindow->ResumeTimeouts(false);
     return NS_OK;
--- a/dom/base/test/mochitest.ini
+++ b/dom/base/test/mochitest.ini
@@ -760,17 +760,17 @@ skip-if = buildapp == 'b2g' || toolkit =
 [test_document_importNode_document.html]
 [test_domparser_null_char.html]
 [test_domparsing.html]
 [test_elementTraversal.html]
 [test_element_closest.html]
 [test_encodeToStringWithMaxLength.html]
 [test_fileapi.html]
 [test_fileapi_slice.html]
-skip-if = toolkit == 'android' #bug 775227
+skip-if = (toolkit == 'android') || e10s # Android: Bug 775227, e10s: Bug 1226477
 [test_getElementById.html]
 [test_html_colors_quirks.html]
 [test_html_colors_standards.html]
 [test_html_in_xhr.html]
 [test_htmlcopyencoder.html]
 [test_htmlcopyencoder.xhtml]
 [test_ipc_messagemanager_blob.html]
 [test_meta_viewport0.html]
--- a/dom/base/test/unit/test_chromeutils_base64.js
+++ b/dom/base/test/unit/test_chromeutils_base64.js
@@ -83,18 +83,20 @@ function testDecode(input, decoded) {
     buffer = ChromeUtils.base64URLDecode(paddedValue, { padding: "require" });
     deepEqual(new Uint8Array(buffer), decoded, paddedValue + " with padding required");
   }
 }
 
 function test_base64URLDecode() {
   throws(_ => ChromeUtils.base64URLDecode(""), /TypeError/,
          "Should require decoding options");
-  throws(_ => ChromeUtils.base64URLEncode("", {}), /TypeError/,
+  throws(_ => ChromeUtils.base64URLDecode("", {}), /TypeError/,
          "Decoding should require the padding option");
+  throws(_ => ChromeUtils.base64URLDecode("", { padding: "chocolate" }),
+         "Decoding should throw for invalid padding policy");
 
   for (let {decoded, encoded} of binaryTests) {
     testDecode(encoded, decoded);
   }
 
   let textEncoder = new TextEncoder("utf-8");
   for (let decoded of Object.keys(textTests)) {
     let expectedBuffer = textEncoder.encode(decoded);
--- a/dom/browser-element/BrowserElementAudioChannel.cpp
+++ b/dom/browser-element/BrowserElementAudioChannel.cpp
@@ -166,17 +166,17 @@ AudioChannel
 BrowserElementAudioChannel::Name() const
 {
   MOZ_ASSERT(NS_IsMainThread());
   return mAudioChannel;
 }
 
 namespace {
 
-class BaseRunnable : public nsRunnable
+class BaseRunnable : public Runnable
 {
 protected:
   nsCOMPtr<nsPIDOMWindowInner> mParentWindow;
   nsCOMPtr<nsPIDOMWindowOuter> mFrameWindow;
   RefPtr<DOMRequest> mRequest;
   AudioChannel mAudioChannel;
 
   virtual void DoWork(AudioChannelService* aService,
--- a/dom/cache/PrincipalVerifier.h
+++ b/dom/cache/PrincipalVerifier.h
@@ -17,17 +17,17 @@ namespace ipc {
   class PBackgroundParent;
 } // namespace ipc
 
 namespace dom {
 namespace cache {
 
 class ManagerId;
 
-class PrincipalVerifier final : public nsRunnable
+class PrincipalVerifier final : public Runnable
 {
 public:
   // An interface to be implemented by code wishing to use the
   // PrincipalVerifier.  Note, the Listener implementation is responsible
   // for calling RemoveListener() on the PrincipalVerifier to clear the
   // weak reference.
   class Listener
   {
--- a/dom/camera/CameraControlImpl.cpp
+++ b/dom/camera/CameraControlImpl.cpp
@@ -21,17 +21,17 @@ CameraControlImpl::CameraControlImpl()
   : mListenerLock("mozilla::camera::CameraControlImpl.Listeners")
   , mPreviewState(CameraControlListener::kPreviewStopped)
   , mHardwareState(CameraControlListener::kHardwareUninitialized)
   , mHardwareStateChangeReason(NS_OK)
 {
   DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
   mCurrentConfiguration.mMode = ICameraControl::kUnspecifiedMode;
 
-  class Delegate : public nsRunnable
+  class Delegate : public Runnable
   {
   public:
     NS_IMETHOD
     Run()
     {
       char stackBaseGuess;
       profiler_register_thread("CameraThread", &stackBaseGuess);
       return NS_OK;
@@ -324,17 +324,17 @@ CameraControlImpl::OnSystemError(CameraC
     CameraControlListener* l = mListeners[i];
     l->OnSystemError(aContext, aError);
   }
 }
 
 // Camera control asynchronous message; these are dispatched from
 //  the Main Thread to the Camera Thread, where they are consumed.
 
-class CameraControlImpl::ControlMessage : public nsRunnable
+class CameraControlImpl::ControlMessage : public Runnable
 {
 public:
   ControlMessage(CameraControlImpl* aCameraControl,
                  CameraControlListener::UserContext aContext)
     : mCameraControl(aCameraControl)
     , mContext(aContext)
   { }
 
--- a/dom/camera/DOMCameraCapabilities.cpp
+++ b/dom/camera/DOMCameraCapabilities.cpp
@@ -17,17 +17,17 @@
 
 namespace mozilla {
 namespace dom {
 
 /**
  * CameraClosedListenerProxy and CameraClosedMessage
  */
 template<class T>
-class CameraClosedMessage : public nsRunnable
+class CameraClosedMessage : public Runnable
 {
 public:
   explicit CameraClosedMessage(nsMainThreadPtrHandle<T> aListener)
     : mListener(aListener)
   {
     DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
   }
 
--- a/dom/camera/DOMCameraControlListener.cpp
+++ b/dom/camera/DOMCameraControlListener.cpp
@@ -25,17 +25,17 @@ DOMCameraControlListener::DOMCameraContr
 }
 
 DOMCameraControlListener::~DOMCameraControlListener()
 {
   DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
 }
 
 // Boilerplate callback runnable
-class DOMCameraControlListener::DOMCallback : public nsRunnable
+class DOMCameraControlListener::DOMCallback : public Runnable
 {
 public:
   explicit DOMCallback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl)
     : mDOMCameraControl(aDOMCameraControl)
   {
     MOZ_COUNT_CTOR(DOMCameraControlListener::DOMCallback);
   }
 
--- a/dom/camera/GonkCameraControl.cpp
+++ b/dom/camera/GonkCameraControl.cpp
@@ -963,17 +963,17 @@ android::sp<android::GonkCameraHardware>
 nsGonkCameraControl::GetCameraHw()
 {
   return mCameraHw;
 }
 
 nsresult
 nsGonkCameraControl::SetThumbnailSize(const Size& aSize)
 {
-  class SetThumbnailSize : public nsRunnable
+  class SetThumbnailSize : public Runnable
   {
   public:
     SetThumbnailSize(nsGonkCameraControl* aCameraControl, const Size& aSize)
       : mCameraControl(aCameraControl)
       , mSize(aSize)
     {
       MOZ_COUNT_CTOR(SetThumbnailSize);
     }
@@ -1081,17 +1081,17 @@ nsGonkCameraControl::RationalizeRotation
   }
 
   return r;
 }
 
 nsresult
 nsGonkCameraControl::SetPictureSize(const Size& aSize)
 {
-  class SetPictureSize : public nsRunnable
+  class SetPictureSize : public Runnable
   {
   public:
     SetPictureSize(nsGonkCameraControl* aCameraControl, const Size& aSize)
       : mCameraControl(aCameraControl)
       , mSize(aSize)
     {
       MOZ_COUNT_CTOR(SetPictureSize);
     }
@@ -1283,17 +1283,17 @@ nsGonkCameraControl::StartRecordingImpl(
   OnRecorderStateChange(CameraControlListener::kRecorderStarted);
   mCapturePoster = aOptions->createPoster;
   return NS_OK;
 }
 
 nsresult
 nsGonkCameraControl::StopRecordingImpl()
 {
-  class RecordingComplete : public nsRunnable
+  class RecordingComplete : public Runnable
   {
   public:
     RecordingComplete(already_AddRefed<DeviceStorageFile> aFile)
       : mFile(aFile)
     { }
 
     ~RecordingComplete() { }
 
@@ -1467,17 +1467,17 @@ nsGonkCameraControl::OnAutoFocusMoving(b
       OnAutoFocusComplete(true, true);
     }
   }
 }
 
 void
 nsGonkCameraControl::OnAutoFocusComplete(bool aSuccess, bool aExpired)
 {
-  class AutoFocusComplete : public nsRunnable
+  class AutoFocusComplete : public Runnable
   {
   public:
     AutoFocusComplete(nsGonkCameraControl* aCameraControl, bool aSuccess, bool aExpired)
       : mCameraControl(aCameraControl)
       , mSuccess(aSuccess)
       , mExpired(aExpired)
     { }
 
@@ -2242,17 +2242,17 @@ void
 nsGonkCameraControl::OnRateLimitPreview(bool aLimit)
 {
   CameraControlImpl::OnRateLimitPreview(aLimit);
 }
 
 void
 nsGonkCameraControl::CreatePoster(Image* aImage, uint32_t aWidth, uint32_t aHeight, int32_t aRotation)
 {
-  class PosterRunnable : public nsRunnable {
+  class PosterRunnable : public Runnable {
   public:
     PosterRunnable(nsGonkCameraControl* aTarget, Image* aImage,
                    uint32_t aWidth, uint32_t aHeight, int32_t aRotation)
       : mTarget(aTarget)
       , mImage(aImage)
       , mWidth(aWidth)
       , mHeight(aHeight)
       , mRotation(aRotation)
--- a/dom/canvas/ImageBitmap.cpp
+++ b/dom/canvas/ImageBitmap.cpp
@@ -908,17 +908,17 @@ protected:
     mPromise->MaybeResolve(mImageBitmap);
   }
 
 private:
   RefPtr<Promise> mPromise;
   RefPtr<ImageBitmap> mImageBitmap;
 };
 
-class FulfillImageBitmapPromiseTask final : public nsRunnable,
+class FulfillImageBitmapPromiseTask final : public Runnable,
                                             public FulfillImageBitmapPromise
 {
 public:
   FulfillImageBitmapPromiseTask(Promise* aPromise, ImageBitmap* aImageBitmap)
   : FulfillImageBitmapPromise(aPromise, aImageBitmap)
   {
   }
 
@@ -1098,17 +1098,17 @@ protected:
   virtual already_AddRefed<ImageBitmap> CreateImageBitmap() = 0;
 
   RefPtr<Promise> mPromise;
   nsCOMPtr<nsIGlobalObject> mGlobalObject;
   RefPtr<mozilla::dom::Blob> mBlob;
   Maybe<IntRect> mCropRect;
 };
 
-class CreateImageBitmapFromBlobTask final : public nsRunnable,
+class CreateImageBitmapFromBlobTask final : public Runnable,
                                             public CreateImageBitmapFromBlob
 {
 public:
   CreateImageBitmapFromBlobTask(Promise* aPromise,
                                 nsIGlobalObject* aGlobal,
                                 Blob& aBlob,
                                 const Maybe<IntRect>& aCropRect)
   :CreateImageBitmapFromBlob(aPromise, aGlobal, aBlob, aCropRect)
--- a/dom/canvas/WebGLContextUtils.cpp
+++ b/dom/canvas/WebGLContextUtils.cpp
@@ -734,30 +734,16 @@ WebGLContext::AssertCachedState()
 {
 #ifdef DEBUG
     MakeContextCurrent();
 
     GetAndFlushUnderlyingGLErrors();
 
     ////////////////
 
-    AssertUintParamCorrect(gl, LOCAL_GL_MAX_COLOR_ATTACHMENTS, mGLMaxColorAttachments);
-    AssertUintParamCorrect(gl, LOCAL_GL_MAX_DRAW_BUFFERS, mGLMaxDrawBuffers);
-
-    if (IsWebGL2() ||
-        IsExtensionEnabled(WebGLExtensionID::WEBGL_draw_buffers))
-    {
-        MOZ_ASSERT(mImplMaxColorAttachments == std::min(mGLMaxColorAttachments,
-                                                        mGLMaxDrawBuffers));
-        MOZ_ASSERT(mImplMaxDrawBuffers == mGLMaxDrawBuffers);
-    } else {
-        MOZ_ASSERT(mImplMaxColorAttachments == 1);
-        MOZ_ASSERT(mImplMaxDrawBuffers == 1);
-    }
-
     // Draw state
     MOZ_ASSERT(gl->fIsEnabled(LOCAL_GL_DEPTH_TEST) == mDepthTestEnabled);
     MOZ_ASSERT(gl->fIsEnabled(LOCAL_GL_DITHER) == mDitherEnabled);
     MOZ_ASSERT_IF(IsWebGL2(),
                   gl->fIsEnabled(LOCAL_GL_RASTERIZER_DISCARD) == mRasterizerDiscardEnabled);
     MOZ_ASSERT(gl->fIsEnabled(LOCAL_GL_SCISSOR_TEST) == mScissorTestEnabled);
     MOZ_ASSERT(gl->fIsEnabled(LOCAL_GL_STENCIL_TEST) == mStencilTestEnabled);
 
--- a/dom/canvas/WebGLQuery.h
+++ b/dom/canvas/WebGLQuery.h
@@ -18,17 +18,17 @@ class WebGLQuery final
     : public nsWrapperCache
     , public WebGLRefCountedObject<WebGLQuery>
     , public LinkedListElement<WebGLQuery>
     , public WebGLContextBoundObject
 {
 public:
     explicit WebGLQuery(WebGLContext* webgl);
 
-    class AvailableRunnable final : public nsRunnable
+    class AvailableRunnable final : public Runnable
     {
     public:
         explicit AvailableRunnable(WebGLQuery* query) : mQuery(query) { }
 
         NS_IMETHOD Run() override {
             mQuery->mCanBeAvailable = true;
             return NS_OK;
         }
--- a/dom/canvas/test/mochitest.ini
+++ b/dom/canvas/test/mochitest.ini
@@ -1,10 +1,9 @@
 [DEFAULT]
-skip-if = (e10s && debug && os == 'win') # Bug 1252677
 support-files =
   android.json
   file_drawImage_document_domain.html
   image_anim-gr.gif
   image_anim-gr.png
   image_anim-poster-gr.png
   image_broken.png
   image_error-early.png
@@ -240,33 +239,26 @@ tags = imagebitmap
 tags = imagebitmap
 [test_imagebitmap_transfer.html]
 tags = imagebitmap
 [test_ImageData_ctor.html]
 [test_isPointInStroke.html]
 [test_mozDashOffset.html]
 [test_mozGetAsFile.html]
 [test_strokeText_throw.html]
-skip-if = (e10s && debug && os == 'win')
 [test_toBlob.html]
-skip-if = (e10s && debug && os == 'win') # bug 1236257
 [test_toDataURL_alpha.html]
-skip-if = (e10s && debug && os == 'win')
 [test_toDataURL_lowercase_ascii.html]
-skip-if = (e10s && debug && os == 'win')
 [test_toDataURL_parameters.html]
-skip-if = (e10s && debug && os == 'win')
 [test_windingRuleUndefined.html]
-skip-if = (e10s && debug && os == 'win')
 [test_2d.fillText.gradient.html]
 skip-if = (buildapp == 'b2g' && toolkit != 'gonk') # bug 1040965
 [test_2d_composite_canvaspattern_setTransform.html]
 [test_createPattern_broken.html]
 [test_setlinedash.html]
-skip-if = (e10s && debug && os == 'win')
 [test_filter.html]
 [test_offscreencanvas_toblob.html]
 tags = offscreencanvas
 [test_offscreencanvas_toimagebitmap.html]
 tags = offscreencanvas
 [test_offscreencanvas_basic_webgl.html]
 tags = offscreencanvas
 [test_offscreencanvas_dynamic_fallback.html]
--- a/dom/canvas/test/webgl-conformance/mochitest-errata.ini
+++ b/dom/canvas/test/webgl-conformance/mochitest-errata.ini
@@ -1,22 +1,19 @@
 # *** WARNING! ***
 # Modification to this file only take effect after running
 # generate-wrappers-and-manifest.py
 
 # See python/mozbuild/mozbuild/mozinfo.py for incoming data.
 
 [DEFAULT]
 subsuite = webgl
-# No e10s yet.
-# 'B2G Desktop Linux' fails to create WebGL contexts.
-# Also skip B2G for now, until we get a handle on the longer tail of emulator
-# bugs.
-# Bug 1136181 disabled on B2G Desktop and Mulet for intermittent failures
-skip-if = e10s || os == 'b2g' || ((os == 'linux') && (buildapp == 'b2g')) || ((os == 'linux') && (buildapp == 'mulet'))
+# Skip B2G for now, until we get a handle on the longer tail of emulator bugs.
+# Bug 1136181 disabled on Mulet for intermittent failures
+skip-if = os == 'b2g' || ((os == 'linux') && (buildapp == 'mulet'))
 
 ########################################################################
 # All
 #[_wrappers/test_always-fail.html]
 #fail-if = 1
 # We'll be able to use `fail-if` after bug 987849.
 
 ########################################################################
--- a/dom/crypto/CryptoBuffer.cpp
+++ b/dom/crypto/CryptoBuffer.cpp
@@ -110,38 +110,36 @@ CryptoBuffer::AppendSECItem(const SECIte
 // * No padding
 // * URL-safe character set
 nsresult
 CryptoBuffer::FromJwkBase64(const nsString& aBase64)
 {
   NS_ConvertUTF16toUTF8 temp(aBase64);
   temp.StripWhitespace();
 
-  Base64URLDecodeOptions options;
   // JWK prohibits padding per RFC 7515, section 2.
-  options.mPadding = Base64URLDecodePadding::Reject;
-  nsresult rv = Base64URLDecode(temp, options, *this);
+  nsresult rv = Base64URLDecode(temp, Base64URLDecodePaddingPolicy::Reject,
+                                *this);
   NS_ENSURE_SUCCESS(rv, rv);
 
   return NS_OK;
 }
 
 nsresult
 CryptoBuffer::ToJwkBase64(nsString& aBase64)
 {
   // Shortcut for the empty octet string
   if (Length() == 0) {
     aBase64.Truncate();
     return NS_OK;
   }
 
   nsAutoCString base64;
-  Base64URLEncodeOptions options;
-  options.mPad = false;
-  nsresult rv = Base64URLEncode(Length(), Elements(), options, base64);
+  nsresult rv = Base64URLEncode(Length(), Elements(),
+                                Base64URLEncodePaddingPolicy::Omit, base64);
   NS_ENSURE_SUCCESS(rv, rv);
 
   CopyASCIItoUTF16(base64, aBase64);
   return NS_OK;
 }
 
 bool
 CryptoBuffer::ToSECItem(PLArenaPool *aArena, SECItem* aItem) const
--- a/dom/devicestorage/DeviceStorageRequestParent.h
+++ b/dom/devicestorage/DeviceStorageRequestParent.h
@@ -36,17 +36,18 @@ public:
 protected:
   ~DeviceStorageRequestParent();
 
 private:
   ThreadSafeAutoRefCnt mRefCnt;
   NS_DECL_OWNINGTHREAD
   DeviceStorageParams mParams;
 
-  class CancelableRunnable : public nsRunnable
+  // XXXkhuey name collision :(
+  class CancelableRunnable : public Runnable
   {
   public:
     explicit CancelableRunnable(DeviceStorageRequestParent* aParent)
       : mParent(aParent)
     {
       mCanceled = !(mParent->AddRunnable(this));
     }
 
--- a/dom/devicestorage/nsDeviceStorage.cpp
+++ b/dom/devicestorage/nsDeviceStorage.cpp
@@ -482,17 +482,17 @@ DeviceStorageTypeChecker::IsSharedMediaR
   return IsMediaType(aType);
 #else
   // For desktop, if the directories have been overridden, then they share
   // a common root.
   return IsMediaType(aType) && DeviceStorageStatics::HasOverrideRootDir();
 #endif
 }
 
-class IOEventComplete : public nsRunnable
+class IOEventComplete : public Runnable
 {
 public:
   IOEventComplete(DeviceStorageFile *aFile, const char *aType)
     : mFile(aFile)
     , mType(aType)
   {
   }
 
--- a/dom/devicestorage/nsDeviceStorage.h
+++ b/dom/devicestorage/nsDeviceStorage.h
@@ -95,17 +95,17 @@ class DeviceStorageUsedSpaceCache final
 {
 public:
   static DeviceStorageUsedSpaceCache* CreateOrGet();
 
   DeviceStorageUsedSpaceCache();
   ~DeviceStorageUsedSpaceCache();
 
 
-  class InvalidateRunnable final : public nsRunnable
+  class InvalidateRunnable final : public mozilla::Runnable
   {
     public:
       InvalidateRunnable(DeviceStorageUsedSpaceCache* aCache, 
                          const nsAString& aStorageName)
         : mCache(aCache)
         , mStorageName(aStorageName) {}
 
       ~InvalidateRunnable() {}
@@ -299,17 +299,17 @@ private:
   mozilla::Mutex mMutex;
   uint32_t mPermissionCache[DEVICE_STORAGE_ACCESS_COUNT];
   bool mShutdown;
 
   static mozilla::Atomic<uint32_t> sLastRequestId;
 };
 
 class DeviceStorageRequest
-  : public nsRunnable
+  : public mozilla::Runnable
 {
 protected:
   DeviceStorageRequest();
 
 public:
   virtual void Initialize(DeviceStorageRequestManager* aManager,
                           already_AddRefed<DeviceStorageFile>&& aFile,
                           uint32_t aRequest);
--- a/dom/events/IMEContentObserver.h
+++ b/dom/events/IMEContentObserver.h
@@ -190,17 +190,17 @@ private:
   nsCOMPtr<nsINode> mEditableNode;
   nsCOMPtr<nsIDocShell> mDocShell;
   nsCOMPtr<nsIEditor> mEditor;
 
   /**
    * Helper classes to notify IME.
    */
 
-  class AChangeEvent: public nsRunnable
+  class AChangeEvent: public Runnable
   {
   protected:
     enum ChangeEventType
     {
       eChangeEventType_Focus,
       eChangeEventType_Selection,
       eChangeEventType_Text,
       eChangeEventType_Position,
--- a/dom/events/IMEStateManager.cpp
+++ b/dom/events/IMEStateManager.cpp
@@ -885,17 +885,17 @@ IMEStateManager::GetNewIMEState(nsPresCo
     ("ISM:   IMEStateManager::GetNewIMEState() returns { mEnabled=%s, "
      "mOpen=%s }",
      GetIMEStateEnabledName(newIMEState.mEnabled),
      GetIMEStateSetOpenName(newIMEState.mOpen)));
   return newIMEState;
 }
 
 // Helper class, used for IME enabled state change notification
-class IMEEnabledStateChangedEvent : public nsRunnable {
+class IMEEnabledStateChangedEvent : public Runnable {
 public:
   explicit IMEEnabledStateChangedEvent(uint32_t aState)
     : mState(aState)
   {
   }
 
   NS_IMETHOD Run()
   {
--- a/dom/events/TextComposition.h
+++ b/dom/events/TextComposition.h
@@ -375,17 +375,17 @@ private:
    * Calculate composition offset then notify composition update to widget
    */
   void NotityUpdateComposition(const WidgetCompositionEvent* aCompositionEvent);
 
   /**
    * CompositionEventDispatcher dispatches the specified composition (or text)
    * event.
    */
-  class CompositionEventDispatcher : public nsRunnable
+  class CompositionEventDispatcher : public Runnable
   {
   public:
     CompositionEventDispatcher(TextComposition* aTextComposition,
                                nsINode* aEventTarget,
                                EventMessage aEventMessage,
                                const nsAString& aData,
                                bool aIsSynthesizedEvent = false);
     NS_IMETHOD Run() override;
--- a/dom/fetch/Fetch.cpp
+++ b/dom/fetch/Fetch.cpp
@@ -101,17 +101,17 @@ public:
 
   void
   OnResponseAvailableInternal(InternalResponse* aResponse) override;
 
 private:
   ~MainThreadFetchResolver();
 };
 
-class MainThreadFetchRunnable : public nsRunnable
+class MainThreadFetchRunnable : public Runnable
 {
   RefPtr<WorkerFetchResolver> mResolver;
   RefPtr<InternalRequest> mRequest;
 
 public:
   MainThreadFetchRunnable(WorkerFetchResolver* aResolver,
                           InternalRequest* aRequest)
     : mResolver(aResolver)
@@ -691,17 +691,17 @@ template <class Derived>
 NS_IMPL_RELEASE(ConsumeBodyDoneObserver<Derived>)
 template <class Derived>
 NS_INTERFACE_MAP_BEGIN(ConsumeBodyDoneObserver<Derived>)
   NS_INTERFACE_MAP_ENTRY(nsIStreamLoaderObserver)
   NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIStreamLoaderObserver)
 NS_INTERFACE_MAP_END
 
 template <class Derived>
-class BeginConsumeBodyRunnable final : public nsRunnable
+class BeginConsumeBodyRunnable final : public Runnable
 {
   FetchBody<Derived>* mFetchBody;
 public:
   explicit BeginConsumeBodyRunnable(FetchBody<Derived>* aBody)
     : mFetchBody(aBody)
   { }
 
   NS_IMETHOD
--- a/dom/filehandle/ActorsParent.cpp
+++ b/dom/filehandle/ActorsParent.cpp
@@ -56,17 +56,17 @@ const uint32_t kThreadLimit = 5;
 const uint32_t kIdleThreadLimit = 1;
 const uint32_t kIdleThreadTimeoutMs = 30000;
 
 const uint32_t kStreamCopyBlockSize = 32768;
 
 } // namespace
 
 class FileHandleThreadPool::FileHandleQueue final
-  : public nsRunnable
+  : public Runnable
 {
   friend class FileHandleThreadPool;
 
   RefPtr<FileHandleThreadPool> mOwningFileHandleThreadPool;
   RefPtr<FileHandle> mFileHandle;
   nsTArray<RefPtr<FileHandleOp>> mQueue;
   RefPtr<FileHandleOp> mCurrentOp;
   bool mShouldFinish;
@@ -565,17 +565,17 @@ protected:
   virtual nsresult
   DoFileWork(FileHandle* aFileHandle) override;
 
   virtual void
   Cleanup() override;
 };
 
 class CopyFileHandleOp::ProgressRunnable final
-  : public nsRunnable
+  : public Runnable
 {
   RefPtr<CopyFileHandleOp> mCopyFileHandleOp;
   uint64_t mProgress;
   uint64_t mProgressMax;
 
 public:
   ProgressRunnable(CopyFileHandleOp* aCopyFileHandleOp,
                    uint64_t aProgress,
--- a/dom/filesystem/FileSystemTaskBase.h
+++ b/dom/filesystem/FileSystemTaskBase.h
@@ -202,17 +202,17 @@ private:
    * owning thread.
    */
   void
   SetRequestResult(const FileSystemResponseValue& aValue);
 };
 
 // This class is the 'alter ego' of FileSystemTaskChildBase in the PBackground
 // world.
-class FileSystemTaskParentBase : public nsRunnable
+class FileSystemTaskParentBase : public Runnable
 {
 public:
   /*
    * Start the task. This must be called from the PBackground thread only.
    */
   void
   Start();
 
--- a/dom/geolocation/nsGeolocation.cpp
+++ b/dom/geolocation/nsGeolocation.cpp
@@ -218,17 +218,17 @@ public:
     if (gs) {
       gs->HandleMozsettingValue(aValue);
     }
   }
 };
 
 NS_IMPL_ISUPPORTS(GeolocationSettingsCallback, nsISettingsServiceCallback)
 
-class RequestPromptEvent : public nsRunnable
+class RequestPromptEvent : public Runnable
 {
 public:
   RequestPromptEvent(nsGeolocationRequest* aRequest, nsWeakPtr aWindow)
     : mRequest(aRequest)
     , mWindow(aWindow)
   {
   }
 
@@ -239,17 +239,17 @@ public:
     return NS_OK;
   }
 
 private:
   RefPtr<nsGeolocationRequest> mRequest;
   nsWeakPtr mWindow;
 };
 
-class RequestAllowEvent : public nsRunnable
+class RequestAllowEvent : public Runnable
 {
 public:
   RequestAllowEvent(int allow, nsGeolocationRequest* request)
     : mAllow(allow),
       mRequest(request)
   {
   }
 
@@ -262,17 +262,17 @@ public:
     return NS_OK;
   }
 
 private:
   bool mAllow;
   RefPtr<nsGeolocationRequest> mRequest;
 };
 
-class RequestSendLocationEvent : public nsRunnable
+class RequestSendLocationEvent : public Runnable
 {
 public:
   RequestSendLocationEvent(nsIDOMGeoPosition* aPosition,
                            nsGeolocationRequest* aRequest)
     : mPosition(aPosition),
       mRequest(aRequest)
   {
   }
--- a/dom/html/HTMLFormElement.h
+++ b/dom/html/HTMLFormElement.h
@@ -431,17 +431,17 @@ protected:
     }
   };
 
   RefPtr<FormPasswordEventDispatcher> mFormPasswordEventDispatcher;
 
   class RemoveElementRunnable;
   friend class RemoveElementRunnable;
 
-  class RemoveElementRunnable : public nsRunnable {
+  class RemoveElementRunnable : public Runnable {
   public:
     explicit RemoveElementRunnable(HTMLFormElement* aForm)
       : mForm(aForm)
     {}
 
     NS_IMETHOD Run() override {
       mForm->HandleDefaultSubmitRemoval();
       return NS_OK;
--- a/dom/html/HTMLImageElement.cpp
+++ b/dom/html/HTMLImageElement.cpp
@@ -72,17 +72,17 @@ static bool IsPreviousSibling(nsINode *a
 #endif
 
 namespace mozilla {
 namespace dom {
 
 // Calls LoadSelectedImage on host element unless it has been superseded or
 // canceled -- this is the synchronous section of "update the image data".
 // https://html.spec.whatwg.org/multipage/embedded-content.html#update-the-image-data
-class ImageLoadTask : public nsRunnable
+class ImageLoadTask : public Runnable
 {
 public:
   ImageLoadTask(HTMLImageElement *aElement, bool aAlwaysLoad)
     : mElement(aElement)
     , mAlwaysLoad(aAlwaysLoad)
   {
     mDocument = aElement->OwnerDoc();
     mDocument->BlockOnload();
@@ -1146,17 +1146,22 @@ HTMLImageElement::UpdateResponsiveSource
     candidateSource = candidateSource->GetNextSibling();
   }
 
   if (!candidateSource) {
     // Ran out of siblings without finding ourself, e.g. XBL magic.
     mResponsiveSelector = nullptr;
   }
 
-  return !hadSelector || mResponsiveSelector;
+  // If we reach this point, either:
+  // - there was no selector originally, and there is not one now
+  // - there was no selector originally, and there is one now
+  // - there was a selector, and there is a different one now
+  // - there was a selector, and there is not one now
+  return hadSelector || mResponsiveSelector;
 }
 
 /*static */ bool
 HTMLImageElement::SupportedPictureSourceType(const nsAString& aType)
 {
   nsAutoString type;
   nsAutoString params;
 
--- a/dom/html/HTMLMediaElement.cpp
+++ b/dom/html/HTMLMediaElement.cpp
@@ -202,17 +202,17 @@ static const double THRESHOLD_LOW_PLAYBA
 // needSelfReference in AddRemoveSelfReference be followed by a call to
 // AddRemoveSelfReference before this element could die!
 // It's especially important if needSelfReference would change to 'true',
 // since if we neglect to add a self-reference, this element might be
 // garbage collected while there are still event listeners that should
 // receive events. If we neglect to remove the self-reference then the element
 // just lives longer than it needs to.
 
-class nsMediaEvent : public nsRunnable
+class nsMediaEvent : public Runnable
 {
 public:
 
   explicit nsMediaEvent(HTMLMediaElement* aElement) :
     mElement(aElement),
     mLoadID(mElement->GetCurrentLoadID()) {}
   ~nsMediaEvent() {}
 
--- a/dom/html/HTMLObjectElement.cpp
+++ b/dom/html/HTMLObjectElement.cpp
@@ -117,17 +117,17 @@ NS_IMPL_NSICONSTRAINTVALIDATION(HTMLObje
 
 static nsIWidget* GetWidget(Element* aElement)
 {
   return nsContentUtils::WidgetForDocument(aElement->OwnerDoc());
 }
 
 Element* HTMLObjectElement::sLastFocused = nullptr; // Weak
 
-class PluginFocusSetter : public nsRunnable
+class PluginFocusSetter : public Runnable
 {
 public:
   PluginFocusSetter(nsIWidget* aWidget, Element* aElement)
   : mWidget(aWidget), mElement(aElement)
   {
   }
 
   NS_IMETHOD Run()
--- a/dom/html/nsGenericHTMLElement.cpp
+++ b/dom/html/nsGenericHTMLElement.cpp
@@ -113,17 +113,17 @@
 using namespace mozilla;
 using namespace mozilla::dom;
 
 /**
  * nsAutoFocusEvent is used to dispatch a focus event when a
  * nsGenericHTMLFormElement is binded to the tree with the autofocus attribute
  * enabled.
  */
-class nsAutoFocusEvent : public nsRunnable
+class nsAutoFocusEvent : public Runnable
 {
 public:
   explicit nsAutoFocusEvent(nsGenericHTMLFormElement* aElement) : mElement(aElement) {}
 
   NS_IMETHOD Run() {
     nsFocusManager* fm = nsFocusManager::GetFocusManager();
     if (!fm) {
       return NS_ERROR_NULL_POINTER;
--- a/dom/html/nsHTMLDocument.cpp
+++ b/dom/html/nsHTMLDocument.cpp
@@ -2519,17 +2519,17 @@ nsHTMLDocument::EndUpdate(nsUpdateType a
   if (reset) {
     mPendingMaybeEditingStateChanged = false;
   }
   MaybeEditingStateChanged();
 }
 
 
 // Helper class, used below in ChangeContentEditableCount().
-class DeferredContentEditableCountChangeEvent : public nsRunnable
+class DeferredContentEditableCountChangeEvent : public Runnable
 {
 public:
   DeferredContentEditableCountChangeEvent(nsHTMLDocument *aDoc,
                                           nsIContent *aElement)
     : mDoc(aDoc)
     , mElement(aElement)
   {
   }
--- a/dom/html/nsTextEditorState.cpp
+++ b/dom/html/nsTextEditorState.cpp
@@ -78,17 +78,17 @@ public:
     mEditor->SetSuppressDispatchingInputEvent(true);
   }
 
 private:
   nsCOMPtr<nsIEditor> mEditor;
   bool mOuterTransaction;
 };
 
-class RestoreSelectionState : public nsRunnable {
+class RestoreSelectionState : public Runnable {
 public:
   RestoreSelectionState(nsTextEditorState *aState, nsTextControlFrame *aFrame)
     : mFrame(aFrame),
       mTextEditorState(aState)
   {
   }
 
   NS_IMETHOD Run() {
@@ -1082,17 +1082,17 @@ nsTextEditorState::GetEditor()
 
 nsISelectionController*
 nsTextEditorState::GetSelectionController() const
 {
   return mSelCon;
 }
 
 // Helper class, used below in BindToFrame().
-class PrepareEditorEvent : public nsRunnable {
+class PrepareEditorEvent : public Runnable {
 public:
   PrepareEditorEvent(nsTextEditorState &aState,
                      nsIContent *aOwnerContent,
                      const nsAString &aCurrentValue)
     : mState(&aState)
     , mOwnerContent(aOwnerContent)
     , mCurrentValue(aCurrentValue)
   {
--- a/dom/indexedDB/ActorsChild.cpp
+++ b/dom/indexedDB/ActorsChild.cpp
@@ -893,17 +893,17 @@ public:
 protected:
   ~WorkerPermissionRequestChildProcessActor()
   {}
 
   virtual bool
   Recv__delete__(const uint32_t& aPermission) override;
 };
 
-class WorkerPermissionChallenge final : public nsRunnable
+class WorkerPermissionChallenge final : public Runnable
                                       , public WorkerFeature
 {
 public:
   WorkerPermissionChallenge(WorkerPrivate* aWorkerPrivate,
                             BackgroundFactoryRequestChild* aActor,
                             IDBFactory* aFactory,
                             const PrincipalInfo& aPrincipalInfo)
     : mWorkerPrivate(aWorkerPrivate)
--- a/dom/indexedDB/ActorsParent.cpp
+++ b/dom/indexedDB/ActorsParent.cpp
@@ -5359,17 +5359,17 @@ private:
   void
   CloseDatabase(DatabaseInfo* aDatabaseInfo);
 
   bool
   CloseDatabaseWhenIdleInternal(const nsACString& aDatabaseId);
 };
 
 class ConnectionPool::ConnectionRunnable
-  : public nsRunnable
+  : public Runnable
 {
 protected:
   DatabaseInfo* mDatabaseInfo;
   nsCOMPtr<nsIEventTarget> mOwningThread;
 
   explicit
   ConnectionRunnable(DatabaseInfo* aDatabaseInfo);
 
@@ -5507,17 +5507,17 @@ protected:
   FinishCallback()
   { }
 
   virtual ~FinishCallback()
   { }
 };
 
 class ConnectionPool::FinishCallbackWrapper final
-  : public nsRunnable
+  : public Runnable
 {
   RefPtr<ConnectionPool> mConnectionPool;
   RefPtr<FinishCallback> mCallback;
   nsCOMPtr<nsIEventTarget> mOwningThread;
   uint64_t mTransactionId;
   bool mHasRunOnce;
 
 public:
@@ -5600,17 +5600,17 @@ public:
   bool
   operator<(const IdleThreadInfo& aOther) const
   {
     return mIdleTime < aOther.mIdleTime;
   }
 };
 
 class ConnectionPool::ThreadRunnable final
-  : public nsRunnable
+  : public Runnable
 {
   // Only touched on the background thread.
   static uint32_t sNextSerialNumber;
 
   // Set at construction for logging.
   const uint32_t mSerialNumber;
 
   // These two values are only modified on the connection thread.
@@ -5685,17 +5685,17 @@ private:
   ~TransactionInfoPair();
 };
 
 /*******************************************************************************
  * Actor class declarations
  ******************************************************************************/
 
 class DatabaseOperationBase
-  : public nsRunnable
+  : public Runnable
   , public mozIStorageProgressHandler
 {
   friend class UpgradeFileIdsFunction;
 
 protected:
   class AutoSetProgressHandler;
 
   typedef nsDataHashtable<nsUint64HashKey, bool> UniqueIndexTable;
@@ -6074,17 +6074,17 @@ private:
                                    override;
 
   virtual bool
   DeallocPBackgroundIDBDatabaseParent(PBackgroundIDBDatabaseParent* aActor)
                                       override;
 };
 
 class WaitForTransactionsHelper final
-  : public nsRunnable
+  : public Runnable
 {
   nsCOMPtr<nsIEventTarget> mOwningThread;
   const nsCString mDatabaseId;
   nsCOMPtr<nsIRunnable> mCallback;
 
   enum class State
   {
     Initial = 0,
@@ -8532,17 +8532,17 @@ private:
                         const int64_t& aFileId,
                         int32_t* aRefCnt,
                         int32_t* aDBRefCnt,
                         int32_t* aSliceRefCnt,
                         bool* aResult) override;
 };
 
 class GetFileReferencesHelper final
-  : public nsRunnable
+  : public Runnable
 {
   PersistenceType mPersistenceType;
   nsCString mOrigin;
   nsString mDatabaseName;
   int64_t mFileId;
 
   mozilla::Mutex mMutex;
   mozilla::CondVar mCondVar;
@@ -8578,17 +8578,17 @@ public:
 
 private:
   ~GetFileReferencesHelper() {}
 
   NS_DECL_NSIRUNNABLE
 };
 
 class FlushPendingFileDeletionsRunnable final
-  : public nsRunnable
+  : public Runnable
 {
 private:
   ~FlushPendingFileDeletionsRunnable()
   { }
 
   NS_DECL_NSIRUNNABLE
 };
 
@@ -8907,17 +8907,17 @@ private:
 
   // Runs on the PBackground thread. Checks to see if there's a queued
   // Maintenance to run.
   void
   ProcessMaintenanceQueue();
 };
 
 class Maintenance final
-  : public nsRunnable
+  : public Runnable
   , public OpenDirectoryListener
 {
   struct DirectoryInfo;
 
   enum class State
   {
     // Newly created on the PBackground thread. Will proceed immediately or be
     // added to the maintenance queue. The next step is either
@@ -9135,17 +9135,17 @@ struct Maintenance::DirectoryInfo final
   {
     MOZ_COUNT_DTOR(Maintenance::DirectoryInfo);
   }
 
   DirectoryInfo(const DirectoryInfo& aOther) = delete;
 };
 
 class DatabaseMaintenance final
-  : public nsRunnable
+  : public Runnable
 {
   // The minimum amount of time that has passed since the last vacuum before we
   // will attempt to analyze the database for fragmentation.
   static const PRTime kMinVacuumAge =
     PRTime(PR_USEC_PER_SEC) * 60 * 60 * 24 * 7;
 
   // If the percent of database pages that are not in contiguous order is higher
   // than this percentage we will attempt a vacuum.
@@ -11924,17 +11924,17 @@ ConnectionPool::ScheduleTransaction(Tran
           created = true;
         } else {
           NS_WARNING("Failed to make new thread!");
         }
       } else if (!mDatabasesPerformingIdleMaintenance.IsEmpty()) {
         // We need a thread right now so force all idle processing to stop by
         // posting a dummy runnable to each thread that might be doing idle
         // maintenance.
-        nsCOMPtr<nsIRunnable> runnable = new nsRunnable();
+        nsCOMPtr<nsIRunnable> runnable = new Runnable();
 
         for (uint32_t index = mDatabasesPerformingIdleMaintenance.Length();
              index > 0;
              index--) {
           DatabaseInfo* dbInfo = mDatabasesPerformingIdleMaintenance[index - 1];
           MOZ_ASSERT(dbInfo);
           MOZ_ASSERT(dbInfo->mThreadInfo.mThread);
 
@@ -12557,17 +12557,17 @@ FinishCallbackWrapper::FinishCallbackWra
 
 ConnectionPool::
 FinishCallbackWrapper::~FinishCallbackWrapper()
 {
   MOZ_ASSERT(!mConnectionPool);
   MOZ_ASSERT(!mCallback);
 }
 
-NS_IMPL_ISUPPORTS_INHERITED0(ConnectionPool::FinishCallbackWrapper, nsRunnable)
+NS_IMPL_ISUPPORTS_INHERITED0(ConnectionPool::FinishCallbackWrapper, Runnable)
 
 nsresult
 ConnectionPool::
 FinishCallbackWrapper::Run()
 {
   MOZ_ASSERT(mConnectionPool);
   MOZ_ASSERT(mCallback);
   MOZ_ASSERT(mOwningThread);
@@ -12617,17 +12617,17 @@ ThreadRunnable::ThreadRunnable()
 
 ConnectionPool::
 ThreadRunnable::~ThreadRunnable()
 {
   MOZ_ASSERT(!mFirstRun);
   MOZ_ASSERT(!mContinueRunning);
 }
 
-NS_IMPL_ISUPPORTS_INHERITED0(ConnectionPool::ThreadRunnable, nsRunnable)
+NS_IMPL_ISUPPORTS_INHERITED0(ConnectionPool::ThreadRunnable, Runnable)
 
 nsresult
 ConnectionPool::
 ThreadRunnable::Run()
 {
 #ifdef MOZ_ENABLE_PROFILER_SPS
   char stackTopGuess;
 #endif // MOZ_ENABLE_PROFILER_SPS
@@ -13330,18 +13330,17 @@ WaitForTransactionsHelper::CallCallback(
   nsCOMPtr<nsIRunnable> callback;
   mCallback.swap(callback);
 
   callback->Run();
 
   mState = State::Complete;
 }
 
-NS_IMPL_ISUPPORTS_INHERITED0(WaitForTransactionsHelper,
-                             nsRunnable)
+NS_IMPL_ISUPPORTS_INHERITED0(WaitForTransactionsHelper, Runnable)
 
 NS_IMETHODIMP
 WaitForTransactionsHelper::Run()
 {
   MOZ_ASSERT(mState != State::Complete);
   MOZ_ASSERT(mCallback);
 
   switch (mState) {
@@ -17742,17 +17741,17 @@ Maintenance::Finish()
 
   mDirectoryLock = nullptr;
 
   mQuotaClient->NoteFinishedMaintenance(this);
 
   mState = State::Complete;
 }
 
-NS_IMPL_ISUPPORTS_INHERITED0(Maintenance, nsRunnable)
+NS_IMPL_ISUPPORTS_INHERITED0(Maintenance, Runnable)
 
 NS_IMETHODIMP
 Maintenance::Run()
 {
   MOZ_ASSERT(mState != State::Complete);
 
   nsresult rv;
 
@@ -19387,17 +19386,17 @@ DatabaseOperationBase::ObjectStoreHasInd
     return rv;
   }
 
   *aHasIndexes = hasResult;
   return NS_OK;
 }
 
 NS_IMPL_ISUPPORTS_INHERITED(DatabaseOperationBase,
-                            nsRunnable,
+                            Runnable,
                             mozIStorageProgressHandler)
 
 NS_IMETHODIMP
 DatabaseOperationBase::OnProgress(mozIStorageConnection* aConnection,
                                   bool* _retval)
 {
   MOZ_ASSERT(!IsOnBackgroundThread());
   MOZ_ASSERT(aConnection);
--- a/dom/indexedDB/FileInfo.cpp
+++ b/dom/indexedDB/FileInfo.cpp
@@ -45,17 +45,17 @@ private:
   virtual int64_t
   Id() const override
   {
     return int64_t(mFileId);
   }
 };
 
 class CleanupFileRunnable final
-  : public nsRunnable
+  : public Runnable
 {
   RefPtr<FileManager> mFileManager;
   int64_t mFileId;
 
 public:
   static void
   DoCleanup(FileManager* aFileManager, int64_t aFileId);
 
@@ -238,17 +238,17 @@ CleanupFileRunnable::DoCleanup(FileManag
   RefPtr<IndexedDatabaseManager> mgr = IndexedDatabaseManager::Get();
   MOZ_ASSERT(mgr);
 
   if (NS_FAILED(mgr->AsyncDeleteFile(aFileManager, aFileId))) {
     NS_WARNING("Failed to delete file asynchronously!");
   }
 }
 
-NS_IMPL_ISUPPORTS_INHERITED0(CleanupFileRunnable, nsRunnable)
+NS_IMPL_ISUPPORTS_INHERITED0(CleanupFileRunnable, Runnable)
 
 NS_IMETHODIMP
 CleanupFileRunnable::Run()
 {
   MOZ_ASSERT(NS_IsMainThread());
 
   DoCleanup(mFileManager, mFileId);
 
--- a/dom/indexedDB/FileSnapshot.cpp
+++ b/dom/indexedDB/FileSnapshot.cpp
@@ -94,17 +94,17 @@ private:
   }
 
   NS_DECL_THREADSAFE_ISUPPORTS
   NS_DECL_NSIINPUTSTREAM
   NS_DECL_NSIIPCSERIALIZABLEINPUTSTREAM
 };
 
 class StreamWrapper::CloseRunnable final
-  : public nsRunnable
+  : public Runnable
 {
   friend class StreamWrapper;
 
   RefPtr<StreamWrapper> mStreamWrapper;
 
 public:
   NS_DECL_ISUPPORTS_INHERITED
 
@@ -278,17 +278,17 @@ StreamWrapper::Deserialize(const InputSt
   if (stream) {
     return stream->Deserialize(aParams, aFileDescriptors);
   }
 
   return false;
 }
 
 NS_IMPL_ISUPPORTS_INHERITED0(StreamWrapper::CloseRunnable,
-                             nsRunnable)
+                             Runnable)
 
 NS_IMETHODIMP
 StreamWrapper::
 CloseRunnable::Run()
 {
   mStreamWrapper->Finish();
 
   return NS_OK;
--- a/dom/indexedDB/ScriptErrorHelper.cpp
+++ b/dom/indexedDB/ScriptErrorHelper.cpp
@@ -11,17 +11,17 @@
 #include "nsContentUtils.h"
 #include "nsIConsoleService.h"
 #include "nsIScriptError.h"
 #include "nsString.h"
 #include "nsThreadUtils.h"
 
 namespace {
 
-class ScriptErrorRunnable final : public nsRunnable
+class ScriptErrorRunnable final : public mozilla::Runnable
 {
   nsString mMessage;
   nsCString mMessageName;
   nsString mFilename;
   uint32_t mLineNumber;
   uint32_t mColumnNumber;
   uint32_t mSeverityFlag;
   uint64_t mInnerWindowID;
--- a/dom/inputport/FakeInputPortService.cpp
+++ b/dom/inputport/FakeInputPortService.cpp
@@ -11,17 +11,17 @@
 #include "nsITimer.h"
 #include "nsServiceManagerUtils.h"
 #include "nsThreadUtils.h"
 
 namespace mozilla {
 namespace dom {
 
 namespace {
-class InputPortServiceNotifyRunnable final : public nsRunnable
+class InputPortServiceNotifyRunnable final : public Runnable
 {
 public:
   InputPortServiceNotifyRunnable(
       nsIInputPortServiceCallback* aCallback,
       nsIArray* aDataList,
       uint16_t aErrorCode = nsIInputPortServiceCallback::INPUTPORT_ERROR_OK)
     : mCallback(aCallback)
     , mDataList(aDataList)
--- a/dom/ipc/Blob.cpp
+++ b/dom/ipc/Blob.cpp
@@ -1451,17 +1451,17 @@ private:
 
 // Each instance of this class will be dispatched to the network stream thread
 // pool to run the first time where it will open the file input stream. It will
 // then dispatch itself back to the owning thread to send the child process its
 // response (assuming that the child has not crashed). The runnable will then
 // dispatch itself to the thread pool again in order to close the file input
 // stream.
 class BlobParent::OpenStreamRunnable final
-  : public nsRunnable
+  : public Runnable
 {
   friend class nsRevocableEventPtr<OpenStreamRunnable>;
 
   // Only safe to access these pointers if mRevoked is false!
   BlobParent* mBlobActor;
   InputStreamParent* mStreamActor;
 
   nsCOMPtr<nsIInputStream> mStream;
@@ -1680,17 +1680,17 @@ private:
     if (!mClosing) {
       return OpenStream();
     }
 
     return CloseStream();
   }
 };
 
-NS_IMPL_ISUPPORTS_INHERITED0(BlobParent::OpenStreamRunnable, nsRunnable)
+NS_IMPL_ISUPPORTS_INHERITED0(BlobParent::OpenStreamRunnable, Runnable)
 
 /*******************************************************************************
  * BlobChild::RemoteBlobImpl Declaration
  ******************************************************************************/
 
 class BlobChild::RemoteBlobImpl
   : public BlobImplBase
   , public nsIRemoteBlob
@@ -1819,17 +1819,17 @@ protected:
   void
   CommonInit(BlobChild* aActor);
 
   void
   Destroy();
 };
 
 class BlobChild::RemoteBlobImpl::CreateStreamHelper final
-  : public nsRunnable
+  : public Runnable
 {
   Monitor mMonitor;
   RefPtr<RemoteBlobImpl> mRemoteBlobImpl;
   RefPtr<RemoteInputStream> mInputStream;
   const uint64_t mStart;
   const uint64_t mLength;
   bool mDone;
 
@@ -2423,17 +2423,17 @@ CreateStreamHelper::RunInternal(RemoteBl
     mDone = true;
     lock.Notify();
   } else {
     mDone = true;
   }
 }
 
 NS_IMPL_ISUPPORTS_INHERITED0(BlobChild::RemoteBlobImpl::CreateStreamHelper,
-                             nsRunnable)
+                             Runnable)
 
 NS_IMETHODIMP
 BlobChild::RemoteBlobImpl::
 CreateStreamHelper::Run()
 {
   MOZ_ASSERT(mRemoteBlobImpl);
   MOZ_ASSERT(mRemoteBlobImpl->ActorEventTargetIsOnCurrentThread());
 
--- a/dom/ipc/ContentParent.cpp
+++ b/dom/ipc/ContentParent.cpp
@@ -1997,17 +1997,17 @@ ContentParent::RecvDeallocateLayerTreeId
   return true;
 }
 
 namespace {
 
 // This runnable only exists to delegate ownership of the
 // ContentParent to this runnable, until it's deleted by the event
 // system.
-struct DelayedDeleteContentParentTask : public nsRunnable
+struct DelayedDeleteContentParentTask : public Runnable
 {
   explicit DelayedDeleteContentParentTask(ContentParent* aObj) : mObj(aObj) { }
 
   // No-op
   NS_IMETHODIMP Run() { return NS_OK; }
 
   RefPtr<ContentParent> mObj;
 };
--- a/dom/ipc/CrashReporterParent.cpp
+++ b/dom/ipc/CrashReporterParent.cpp
@@ -163,17 +163,17 @@ CrashReporterParent::FinalizeChildData()
 
   if (NS_IsMainThread()) {
     // Inline, this is the main thread. Get this done.
     NotifyCrashService();
     return;
   }
 
   nsCOMPtr<nsIThread> mainThread = do_GetMainThread();
-  class NotifyOnMainThread : public nsRunnable
+  class NotifyOnMainThread : public Runnable
   {
   public:
     explicit NotifyOnMainThread(CrashReporterParent* aCR)
       : mCR(aCR)
     { }
 
     NS_IMETHOD Run() {
       mCR->NotifyCrashService();
--- a/dom/ipc/FilePickerParent.h
+++ b/dom/ipc/FilePickerParent.h
@@ -71,17 +71,17 @@ class FilePickerParent : public PFilePic
     virtual ~FilePickerShownCallback() {}
     FilePickerParent* mFilePickerParent;
   };
 
  private:
   bool CreateFilePicker();
 
   // This runnable is used to do some I/O operation on a separate thread.
-  class IORunnable : public nsRunnable
+  class IORunnable : public Runnable
   {
     FilePickerParent* mFilePickerParent;
     nsTArray<nsCOMPtr<nsIFile>> mFiles;
     nsTArray<BlobImplOrString> mResults;
     nsCOMPtr<nsIEventTarget> mEventTarget;
     bool mIsDirectory;
 
   public:
--- a/dom/ipc/PBrowser.ipdl
+++ b/dom/ipc/PBrowser.ipdl
@@ -477,17 +477,24 @@ parent:
                                      double aPointerPressure,
                                      uint32_t aPointerOrientation,
                                      uint64_t aObserverId);
     async SynthesizeNativeTouchTap(LayoutDeviceIntPoint aPoint,
                                    bool aLongTap,
                                    uint64_t aObserverId);
     async ClearNativeTouchSequence(uint64_t aObserverId);
 
+    /**
+     * Returns the number of tabs in the window via the out parameter.
+     * If the number of tabs can't be determined, returns 0.
+     *
+     * @param aValue where to store the tab count
+     */
     sync GetTabCount() returns (uint32_t value);
+
 child:
     async NativeSynthesisResponse(uint64_t aObserverId, nsCString aResponse);
 
 
 parent:
 
     /**
      * Child informs the parent that the graphics objects are ready for
--- a/dom/ipc/ProcessHangMonitor.cpp
+++ b/dom/ipc/ProcessHangMonitor.cpp
@@ -551,17 +551,17 @@ HangMonitorParent::Open(Transport* aTran
                         MessageLoop* aIOLoop)
 {
   MOZ_RELEASE_ASSERT(MessageLoop::current() == MonitorLoop());
 
   DebugOnly<bool> ok = PProcessHangMonitorParent::Open(aTransport, aPid, aIOLoop);
   MOZ_ASSERT(ok);
 }
 
-class HangObserverNotifier final : public nsRunnable
+class HangObserverNotifier final : public Runnable
 {
 public:
   HangObserverNotifier(HangMonitoredProcess* aProcess,
                        const HangData& aHangData,
                        const nsString& aBrowserDumpId)
     : mProcess(aProcess),
       mHangData(aHangData),
       mBrowserDumpId(aBrowserDumpId)
@@ -632,17 +632,17 @@ HangMonitorParent::RecvHangEvidence(cons
 
   nsCOMPtr<nsIRunnable> notifier =
     new HangObserverNotifier(mProcess, aHangData, crashId);
   NS_DispatchToMainThread(notifier);
 
   return true;
 }
 
-class ClearHangNotifier final : public nsRunnable
+class ClearHangNotifier final : public Runnable
 {
 public:
   explicit ClearHangNotifier(HangMonitoredProcess* aProcess)
     : mProcess(aProcess)
   {}
 
   NS_IMETHOD
   Run()
--- a/dom/ipc/TabChild.cpp
+++ b/dom/ipc/TabChild.cpp
@@ -332,17 +332,17 @@ public:
     }
 
     void FireCallback() const
     {
         mCallback->OnCachedFileDescriptor(mPath, mFileDescriptor);
     }
 };
 
-class TabChild::CachedFileDescriptorCallbackRunnable : public nsRunnable
+class TabChild::CachedFileDescriptorCallbackRunnable : public Runnable
 {
     typedef TabChild::CachedFileDescriptorInfo CachedFileDescriptorInfo;
 
     nsAutoPtr<CachedFileDescriptorInfo> mInfo;
 
 public:
     explicit CachedFileDescriptorCallbackRunnable(CachedFileDescriptorInfo* aInfo)
       : mInfo(aInfo)
@@ -368,17 +368,17 @@ private:
         MOZ_ASSERT(mInfo);
 
         mInfo->FireCallback();
         return NS_OK;
     }
 };
 
 class TabChild::DelayedDeleteRunnable final
-  : public nsRunnable
+  : public Runnable
 {
     RefPtr<TabChild> mTabChild;
 
 public:
     explicit DelayedDeleteRunnable(TabChild* aTabChild)
       : mTabChild(aTabChild)
     {
         MOZ_ASSERT(NS_IsMainThread());
--- a/dom/ipc/TabParent.cpp
+++ b/dom/ipc/TabParent.cpp
@@ -105,17 +105,17 @@ using namespace mozilla::layout;
 using namespace mozilla::services;
 using namespace mozilla::widget;
 using namespace mozilla::jsipc;
 
 // The flags passed by the webProgress notifications are 16 bits shifted
 // from the ones registered by webProgressListeners.
 #define NOTIFY_FLAG_SHIFT 16
 
-class OpenFileAndSendFDRunnable : public nsRunnable
+class OpenFileAndSendFDRunnable : public mozilla::Runnable
 {
     const nsString mPath;
     RefPtr<TabParent> mTabParent;
     nsCOMPtr<nsIEventTarget> mEventTarget;
     PRFileDesc* mFD;
 
 public:
     OpenFileAndSendFDRunnable(const nsAString& aPath, TabParent* aTabParent)
@@ -2830,17 +2830,17 @@ TabParent::SetHasContentOpener(bool aHas
 NS_IMETHODIMP
 TabParent::NavigateByKey(bool aForward, bool aForDocumentNavigation)
 {
   Unused << SendNavigateByKey(aForward, aForDocumentNavigation);
   return NS_OK;
 }
 
 class LayerTreeUpdateRunnable final
-  : public nsRunnable
+  : public mozilla::Runnable
 {
   uint64_t mLayersId;
   bool mActive;
 
 public:
   explicit LayerTreeUpdateRunnable(uint64_t aLayersId, bool aActive)
     : mLayersId(aLayersId), mActive(aActive) {}
 
@@ -3282,22 +3282,24 @@ TabParent::AudioChannelChangeNotificatio
 
     window = win;
   }
 }
 
 bool
 TabParent::RecvGetTabCount(uint32_t* aValue)
 {
+  *aValue = 0;
+
   nsCOMPtr<nsIXULBrowserWindow> xulBrowserWindow = GetXULBrowserWindow();
-  NS_ENSURE_TRUE(xulBrowserWindow, false);
+  NS_ENSURE_TRUE(xulBrowserWindow, true);
 
   uint32_t tabCount;
   nsresult rv = xulBrowserWindow->GetTabCount(&tabCount);
-  NS_ENSURE_SUCCESS(rv, false);
+  NS_ENSURE_SUCCESS(rv, true);
 
   *aValue = tabCount;
   return true;
 }
 
 NS_IMETHODIMP
 FakeChannel::OnAuthAvailable(nsISupports *aContext, nsIAuthInformation *aAuthInfo)
 {
--- a/dom/media/AudioConverter.cpp
+++ b/dom/media/AudioConverter.cpp
@@ -2,16 +2,17 @@
 /* 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 "AudioConverter.h"
 #include <string.h>
 #include <speex/speex_resampler.h>
+#include <cmath>
 
 /*
  *  Parts derived from MythTV AudioConvert Class
  *  Created by Jean-Yves Avenard.
  *
  *  Copyright (C) Bubblestuff Pty Ltd 2013
  *  Copyright (C) foobum@gmail.com 2010
  */
@@ -21,69 +22,59 @@ namespace mozilla {
 AudioConverter::AudioConverter(const AudioConfig& aIn, const AudioConfig& aOut)
   : mIn(aIn)
   , mOut(aOut)
   , mResampler(nullptr)
 {
   MOZ_DIAGNOSTIC_ASSERT(aIn.Format() == aOut.Format() &&
                         aIn.Interleaved() == aOut.Interleaved(),
                         "No format or rate conversion is supported at this stage");
-  MOZ_DIAGNOSTIC_ASSERT((aIn.Channels() > aOut.Channels() && aOut.Channels() <= 2) ||
+  MOZ_DIAGNOSTIC_ASSERT(aOut.Channels() <= 2 ||
                         aIn.Channels() == aOut.Channels(),
-                        "Only downmixing to mono or stereo is supported at this stage");
+                        "Only down/upmixing to mono or stereo is supported at this stage");
   MOZ_DIAGNOSTIC_ASSERT(aOut.Interleaved(), "planar audio format not supported");
   mIn.Layout().MappingTable(mOut.Layout(), mChannelOrderMap);
   if (aIn.Rate() != aOut.Rate()) {
-    int error;
-    mResampler = speex_resampler_init(aOut.Channels(),
-                                      aIn.Rate(),
-                                      aOut.Rate(),
-                                      SPEEX_RESAMPLER_QUALITY_DEFAULT,
-                                      &error);
-
-    if (error == RESAMPLER_ERR_SUCCESS) {
-      speex_resampler_skip_zeros(mResampler);
-    } else {
-      NS_WARNING("Failed to initialize resampler.");
-      mResampler = nullptr;
-    }
+    RecreateResampler();
   }
 }
 
 AudioConverter::~AudioConverter()
 {
   if (mResampler) {
     speex_resampler_destroy(mResampler);
     mResampler = nullptr;
   }
 }
 
 bool
 AudioConverter::CanWorkInPlace() const
 {
   bool needDownmix = mIn.Channels() > mOut.Channels();
+  bool needUpmix = mIn.Channels() < mOut.Channels();
   bool canDownmixInPlace =
     mIn.Channels() * AudioConfig::SampleSize(mIn.Format()) >=
     mOut.Channels() * AudioConfig::SampleSize(mOut.Format());
   bool needResample = mIn.Rate() != mOut.Rate();
   bool canResampleInPlace = mIn.Rate() >= mOut.Rate();
   // We should be able to work in place if 1s of audio input takes less space
   // than 1s of audio output. However, as we downmix before resampling we can't
   // perform any upsampling in place (e.g. if incoming rate >= outgoing rate)
-  return (!needDownmix || canDownmixInPlace) &&
+  return !needUpmix && (!needDownmix || canDownmixInPlace) &&
          (!needResample || canResampleInPlace);
 }
 
 size_t
 AudioConverter::ProcessInternal(void* aOut, const void* aIn, size_t aFrames)
 {
   if (mIn.Channels() > mOut.Channels()) {
     return DownmixAudio(aOut, aIn, aFrames);
-  } else if (mIn.Layout() != mOut.Layout() &&
-      CanReorderAudio()) {
+  } else if (mIn.Channels() < mOut.Channels()) {
+    return UpmixAudio(aOut, aIn, aFrames);
+  } else if (mIn.Layout() != mOut.Layout() && CanReorderAudio()) {
     ReOrderInterleavedChannels(aOut, aIn, aFrames);
   } else if (aIn != aOut) {
     memmove(aOut, aIn, FramesOutToBytes(aFrames));
   }
   return aFrames;
 }
 
 // Reorder interleaved channels.
@@ -109,20 +100,17 @@ void
 }
 
 void
 AudioConverter::ReOrderInterleavedChannels(void* aOut, const void* aIn,
                                            size_t aFrames) const
 {
   MOZ_DIAGNOSTIC_ASSERT(mIn.Channels() == mOut.Channels());
 
-  if (mOut.Layout() == mIn.Layout()) {
-    return;
-  }
-  if (mOut.Channels() == 1) {
+  if (mOut.Channels() == 1 || mOut.Layout() == mIn.Layout()) {
     // If channel count is 1, planar and non-planar formats are the same and
     // there's nothing to reorder.
     if (aOut != aIn) {
       memmove(aOut, aIn, FramesOutToBytes(aFrames));
     }
     return;
   }
 
@@ -226,26 +214,26 @@ AudioConverter::DownmixAudio(void* aOut,
     aIn = aOut;
     channels = 2;
   }
 
   if (mOut.Channels() == 1) {
     if (mIn.Format() == AudioConfig::FORMAT_FLT) {
       const float* in = static_cast<const float*>(aIn);
       float* out = static_cast<float*>(aOut);
-      for (uint32_t fIdx = 0; fIdx < aFrames; ++fIdx) {
+      for (size_t fIdx = 0; fIdx < aFrames; ++fIdx) {
         float sample = 0.0;
         // The sample of the buffer would be interleaved.
         sample = (in[fIdx*channels] + in[fIdx*channels + 1]) * 0.5;
         *out++ = sample;
       }
     } else if (mIn.Format() == AudioConfig::FORMAT_S16) {
       const int16_t* in = static_cast<const int16_t*>(aIn);
       int16_t* out = static_cast<int16_t*>(aOut);
-      for (uint32_t fIdx = 0; fIdx < aFrames; ++fIdx) {
+      for (size_t fIdx = 0; fIdx < aFrames; ++fIdx) {
         int32_t sample = 0.0;
         // The sample of the buffer would be interleaved.
         sample = (in[fIdx*channels] + in[fIdx*channels + 1]) * 0.5;
         *out++ = sample;
       }
     } else {
       MOZ_DIAGNOSTIC_ASSERT(false, "Unsupported data type");
     }
@@ -257,37 +245,136 @@ size_t
 AudioConverter::ResampleAudio(void* aOut, const void* aIn, size_t aFrames)
 {
   if (!mResampler) {
     return 0;
   }
   uint32_t outframes = ResampleRecipientFrames(aFrames);
   uint32_t inframes = aFrames;
 
+  int error;
   if (mOut.Format() == AudioConfig::FORMAT_FLT) {
     const float* in = reinterpret_cast<const float*>(aIn);
     float* out = reinterpret_cast<float*>(aOut);
-    speex_resampler_process_interleaved_float(mResampler, in, &inframes,
-                                              out, &outframes);
+    error =
+      speex_resampler_process_interleaved_float(mResampler, in, &inframes,
+                                                out, &outframes);
   } else if (mOut.Format() == AudioConfig::FORMAT_S16) {
     const int16_t* in = reinterpret_cast<const int16_t*>(aIn);
     int16_t* out = reinterpret_cast<int16_t*>(aOut);
-    speex_resampler_process_interleaved_int(mResampler, in, &inframes,
-                                            out, &outframes);
+    error =
+      speex_resampler_process_interleaved_int(mResampler, in, &inframes,
+                                              out, &outframes);
   } else {
     MOZ_DIAGNOSTIC_ASSERT(false, "Unsupported data type");
   }
+  MOZ_ASSERT(error == RESAMPLER_ERR_SUCCESS);
+  if (error != RESAMPLER_ERR_SUCCESS) {
+    speex_resampler_destroy(mResampler);
+    mResampler = nullptr;
+    return 0;
+  }
   MOZ_ASSERT(inframes == aFrames, "Some frames will be dropped");
   return outframes;
 }
 
+void
+AudioConverter::RecreateResampler()
+{
+  if (mResampler) {
+    speex_resampler_destroy(mResampler);
+  }
+  int error;
+  mResampler = speex_resampler_init(mOut.Channels(),
+                                    mIn.Rate(),
+                                    mOut.Rate(),
+                                    SPEEX_RESAMPLER_QUALITY_DEFAULT,
+                                    &error);
+
+  if (error == RESAMPLER_ERR_SUCCESS) {
+    speex_resampler_skip_zeros(mResampler);
+  } else {
+    NS_WARNING("Failed to initialize resampler.");
+    mResampler = nullptr;
+  }
+}
+
+size_t
+AudioConverter::DrainResampler(void* aOut)
+{
+  if (!mResampler) {
+    return 0;
+  }
+  int frames = speex_resampler_get_input_latency(mResampler);
+  AlignedByteBuffer buffer(FramesOutToBytes(frames));
+  if (!buffer) {
+    // OOM
+    return 0;
+  }
+  frames = ResampleAudio(aOut, buffer.Data(), frames);
+  // Tore down the resampler as it's easier than handling follow-up.
+  RecreateResampler();
+  return frames;
+}
+
+size_t
+AudioConverter::UpmixAudio(void* aOut, const void* aIn, size_t aFrames) const
+{
+  MOZ_ASSERT(mIn.Format() == AudioConfig::FORMAT_S16 ||
+             mIn.Format() == AudioConfig::FORMAT_FLT);
+  MOZ_ASSERT(mIn.Channels() < mOut.Channels());
+  MOZ_ASSERT(mIn.Channels() == 1, "Can only upmix mono for now");
+  MOZ_ASSERT(mOut.Channels() == 2, "Can only upmix to stereo for now");
+
+  if (mOut.Channels() != 2) {
+    return 0;
+  }
+
+  // Upmix mono to stereo.
+  // This is a very dumb mono to stereo upmixing, power levels are preserved
+  // following the calculation: left = right = -3dB*mono.
+  if (mIn.Format() == AudioConfig::FORMAT_FLT) {
+    const float m3db = std::sqrt(0.5); // -3dB = sqrt(1/2)
+    const float* in = static_cast<const float*>(aIn);
+    float* out = static_cast<float*>(aOut);
+    for (size_t fIdx = 0; fIdx < aFrames; ++fIdx) {
+      float sample = in[fIdx] * m3db;
+      // The samples of the buffer would be interleaved.
+      *out++ = sample;
+      *out++ = sample;
+    }
+  } else if (mIn.Format() == AudioConfig::FORMAT_S16) {
+    const int16_t* in = static_cast<const int16_t*>(aIn);
+    int16_t* out = static_cast<int16_t*>(aOut);
+    for (size_t fIdx = 0; fIdx < aFrames; ++fIdx) {
+      int16_t sample = ((int32_t)in[fIdx] * 11585) >> 14; // close enough to i*sqrt(0.5)
+      // The samples of the buffer would be interleaved.
+      *out++ = sample;
+      *out++ = sample;
+    }
+  } else {
+    MOZ_DIAGNOSTIC_ASSERT(false, "Unsupported data type");
+  }
+
+  return aFrames;
+}
+
 size_t
 AudioConverter::ResampleRecipientFrames(size_t aFrames) const
 {
-  return (uint64_t)aFrames * mOut.Rate() / mIn.Rate() + 1;
+  if (!aFrames && mIn.Rate() != mOut.Rate()) {
+    // The resampler will be drained, account for frames currently buffered
+    // in the resampler.
+    if (!mResampler) {
+      return 0;
+    }
+    return speex_resampler_get_output_latency(mResampler);
+  } else {
+    return (uint64_t)aFrames * mOut.Rate() / mIn.Rate() + 1;
+  }
 }
 
 size_t
 AudioConverter::FramesOutToSamples(size_t aFrames) const
 {
   return aFrames * mOut.Channels();
 }
 
--- a/dom/media/AudioConverter.h
+++ b/dom/media/AudioConverter.h
@@ -118,16 +118,18 @@ typedef AudioDataBuffer<AudioConfig::FOR
 class AudioConverter {
 public:
   AudioConverter(const AudioConfig& aIn, const AudioConfig& aOut);
   ~AudioConverter();
 
   // Convert the AudioDataBuffer.
   // Conversion will be done in place if possible. Otherwise a new buffer will
   // be returned.
+  // Providing an empty buffer and resampling is expected, the resampler
+  // will be drained.
   template <AudioConfig::SampleFormat Format, typename Value>
   AudioDataBuffer<Format, Value> Process(AudioDataBuffer<Format, Value>&& aBuffer)
   {
     MOZ_DIAGNOSTIC_ASSERT(mIn.Format() == mOut.Format() && mIn.Format() == Format);
     AudioDataBuffer<Format, Value> buffer = Move(aBuffer);
     if (CanWorkInPlace()) {
       size_t frames = SamplesInToFrames(buffer.Length());
       frames = ProcessInternal(buffer.Data(), buffer.Data(), frames);
@@ -147,32 +149,36 @@ public:
     MOZ_DIAGNOSTIC_ASSERT(mIn.Format() == mOut.Format() && mIn.Format() == Format);
     // Perform the downmixing / reordering in temporary buffer.
     size_t frames = SamplesInToFrames(aBuffer.Length());
     AlignedBuffer<Value> temp1;
     if (!temp1.SetLength(FramesOutToSamples(frames))) {
       return AudioDataBuffer<Format, Value>(Move(temp1));
     }
     frames = ProcessInternal(temp1.Data(), aBuffer.Data(), frames);
-    if (!frames || mIn.Rate() == mOut.Rate()) {
+    if (mIn.Rate() == mOut.Rate()) {
       temp1.SetLength(FramesOutToSamples(frames));
       return AudioDataBuffer<Format, Value>(Move(temp1));
     }
 
     // At this point, temp1 contains the buffer reordered and downmixed.
     // If we are downsampling we can re-use it.
     AlignedBuffer<Value>* outputBuffer = &temp1;
     AlignedBuffer<Value> temp2;
-    if (mOut.Rate() > mIn.Rate()) {
-      // We are upsampling, we can't work in place. Allocate another temporary
-      // buffer where the upsampling will occur.
+    if (!frames || mOut.Rate() > mIn.Rate()) {
+      // We are upsampling or about to drain, we can't work in place.
+      // Allocate another temporary buffer where the upsampling will occur.
       temp2.SetLength(FramesOutToSamples(ResampleRecipientFrames(frames)));
       outputBuffer = &temp2;
     }
-    frames = ResampleAudio(outputBuffer->Data(), temp1.Data(), frames);
+    if (!frames) {
+      frames = DrainResampler(outputBuffer->Data());
+    } else {
+      frames = ResampleAudio(outputBuffer->Data(), temp1.Data(), frames);
+    }
     outputBuffer->SetLength(FramesOutToSamples(frames));
     return AudioDataBuffer<Format, Value>(Move(*outputBuffer));
   }
 
   // Attempt to convert the AudioDataBuffer in place.
   // Will return 0 if the conversion wasn't possible.
   template <typename Value>
   size_t Process(Value* aBuffer, size_t aFrames)
@@ -208,22 +214,25 @@ private:
    * aIn   : source buffer
    * aSamples: number of frames in source buffer
    *
    * Return Value: number of frames converted or 0 if error
    */
   size_t ProcessInternal(void* aOut, const void* aIn, size_t aFrames);
   void ReOrderInterleavedChannels(void* aOut, const void* aIn, size_t aFrames) const;
   size_t DownmixAudio(void* aOut, const void* aIn, size_t aFrames) const;
+  size_t UpmixAudio(void* aOut, const void* aIn, size_t aFrames) const;
 
   size_t FramesOutToSamples(size_t aFrames) const;
   size_t SamplesInToFrames(size_t aSamples) const;
   size_t FramesOutToBytes(size_t aFrames) const;
 
   // Resampler context.
   SpeexResamplerState* mResampler;
   size_t ResampleAudio(void* aOut, const void* aIn, size_t aFrames);
   size_t ResampleRecipientFrames(size_t aFrames) const;
+  void RecreateResampler();
+  size_t DrainResampler(void* aOut);
 };
 
 } // namespace mozilla
 
 #endif /* AudioConverter_h */
--- a/dom/media/AudioStream.cpp
+++ b/dom/media/AudioStream.cpp
@@ -124,17 +124,16 @@ AudioStream::AudioStream(DataSource& aSo
   , mInRate(0)
   , mOutRate(0)
   , mChannels(0)
   , mOutChannels(0)
   , mAudioClock(this)
   , mTimeStretcher(nullptr)
   , mDumpFile(nullptr)
   , mState(INITIALIZED)
-  , mIsMonoAudioEnabled(gfxPrefs::MonoAudio())
   , mDataSource(aSource)
 {
 }
 
 AudioStream::~AudioStream()
 {
   LOG("deleted, state %d", mState);
   MOZ_ASSERT(mState == SHUTDOWN && !mCubebStream,
@@ -326,17 +325,17 @@ AudioStream::Init(uint32_t aNumChannels,
   if (!CubebUtils::GetCubebContext()) {
     return NS_ERROR_FAILURE;
   }
 
   MOZ_LOG(gAudioStreamLog, LogLevel::Debug,
     ("%s  channels: %d, rate: %d for %p", __FUNCTION__, aNumChannels, aRate, this));
   mInRate = mOutRate = aRate;
   mChannels = aNumChannels;
-  mOutChannels = mIsMonoAudioEnabled ? 1 : aNumChannels;
+  mOutChannels = aNumChannels;
 
   mDumpFile = OpenDumpFile(this);
 
   cubeb_stream_params params;
   params.rate = aRate;
   params.channels = mOutChannels;
 #if defined(__ANDROID__)
 #if defined(MOZ_B2G)
@@ -348,21 +347,16 @@ AudioStream::Init(uint32_t aNumChannels,
   if (params.stream_type == CUBEB_STREAM_TYPE_MAX) {
     return NS_ERROR_INVALID_ARG;
   }
 #endif
 
   params.format = ToCubebFormat<AUDIO_OUTPUT_FORMAT>::value;
   mAudioClock.Init();
 
-  if (mIsMonoAudioEnabled) {
-    AudioConfig inConfig(mChannels, mInRate);
-    AudioConfig outConfig(mOutChannels, mOutRate);
-    mAudioConverter = MakeUnique<AudioConverter>(inConfig, outConfig);
-  }
   return OpenCubeb(params);
 }
 
 // This code used to live inside AudioStream::Init(), but on Mac (others?)
 // it has been known to take 300-800 (or even 8500) ms to execute(!)
 nsresult
 AudioStream::OpenCubeb(cubeb_stream_params &aParams)
 {
@@ -547,31 +541,27 @@ AudioStream::GetPositionInFramesUnlocked
 bool
 AudioStream::IsPaused()
 {
   MonitorAutoLock mon(mMonitor);
   return mState == STOPPED;
 }
 
 bool
-AudioStream::Downmix(Chunk* aChunk)
+AudioStream::IsValidAudioFormat(Chunk* aChunk)
 {
   if (aChunk->Rate() != mInRate) {
     LOGW("mismatched sample %u, mInRate=%u", aChunk->Rate(), mInRate);
     return false;
   }
 
   if (aChunk->Channels() > 8) {
     return false;
   }
 
-  if (mAudioConverter) {
-    mAudioConverter->Process(aChunk->GetWritable(), aChunk->Frames());
-  }
-
   return true;
 }
 
 void
 AudioStream::GetUnprocessed(AudioBufferWriter& aWriter)
 {
   mMonitor.AssertCurrentThreadOwns();
 
@@ -590,20 +580,20 @@ AudioStream::GetUnprocessed(AudioBufferW
   }
 
   while (aWriter.Available() > 0) {
     UniquePtr<Chunk> c = mDataSource.PopFrames(aWriter.Available());
     if (c->Frames() == 0) {
       break;
     }
     MOZ_ASSERT(c->Frames() <= aWriter.Available());
-    if (Downmix(c.get())) {
+    if (IsValidAudioFormat(c.get())) {
       aWriter.Write(c->Data(), c->Frames());
     } else {
-      // Write silence if downmixing fails.
+      // Write silence if invalid format.
       aWriter.WriteZeros(c->Frames());
     }
   }
 }
 
 void
 AudioStream::GetTimeStretched(AudioBufferWriter& aWriter)
 {
@@ -618,20 +608,20 @@ AudioStream::GetTimeStretched(AudioBuffe
   uint32_t toPopFrames = ceil(aWriter.Available() * playbackRate);
 
   while (mTimeStretcher->numSamples() < aWriter.Available()) {
     UniquePtr<Chunk> c = mDataSource.PopFrames(toPopFrames);
     if (c->Frames() == 0) {
       break;
     }
     MOZ_ASSERT(c->Frames() <= toPopFrames);
-    if (Downmix(c.get())) {
+    if (IsValidAudioFormat(c.get())) {
       mTimeStretcher->putSamples(c->Data(), c->Frames());
     } else {
-      // Write silence if downmixing fails.
+      // Write silence if invalid format.
       AutoTArray<AudioDataValue, 1000> buf;
       buf.SetLength(mOutChannels * c->Frames());
       memset(buf.Elements(), 0, buf.Length() * sizeof(AudioDataValue));
       mTimeStretcher->putSamples(buf.Elements(), c->Frames());
     }
   }
 
   auto timeStretcher = mTimeStretcher;
--- a/dom/media/AudioStream.h
+++ b/dom/media/AudioStream.h
@@ -281,16 +281,21 @@ public:
 
   // Return the position, measured in audio frames played since the stream
   // was opened, of the audio hardware.  Thread-safe.
   int64_t GetPositionInFrames();
 
   // Returns true when the audio stream is paused.
   bool IsPaused();
 
+  static uint32_t GetPreferredRate()
+  {
+    CubebUtils::InitPreferredSampleRate();
+    return CubebUtils::PreferredSampleRate();
+  }
   uint32_t GetRate() { return mOutRate; }
   uint32_t GetChannels() { return mChannels; }
   uint32_t GetOutChannels() { return mOutChannels; }
 
   // Set playback rate as a multiple of the intrinsic playback rate. This is to
   // be called only with aPlaybackRate > 0.0.
   nsresult SetPlaybackRate(double aPlaybackRate);
   // Switch between resampling (if false) and time stretching (if true, default).
@@ -323,18 +328,19 @@ private:
   }
 
 
   long DataCallback(void* aBuffer, long aFrames);
   void StateCallback(cubeb_state aState);
 
   nsresult EnsureTimeStretcherInitializedUnlocked();
 
-  // Return true if downmixing succeeds otherwise false.
-  bool Downmix(Chunk* aChunk);
+  // Return true if audio frames are valid (correct sampling rate and valid
+  // channel count) otherwise false.
+  bool IsValidAudioFormat(Chunk* aChunk);
 
   void GetUnprocessed(AudioBufferWriter& aWriter);
   void GetTimeStretched(AudioBufferWriter& aWriter);
 
   void StartUnlocked();
 
   // The monitor is held to protect all access to member variables.
   Monitor mMonitor;
@@ -364,19 +370,15 @@ private:
     STOPPED,     // Stopped by a call to Pause().
     DRAINED,     // StateCallback has indicated that the drain is complete.
     ERRORED,     // Stream disabled due to an internal error.
     SHUTDOWN     // Shutdown has been called
   };
 
   StreamState mState;
   bool mIsFirst;
-  // Get this value from the preference, if true, we would downmix the stereo.
-  bool mIsMonoAudioEnabled;
 
   DataSource& mDataSource;
-
-  UniquePtr<AudioConverter> mAudioConverter;
 };
 
 } // namespace mozilla
 
 #endif
--- a/dom/media/FileBlockCache.h
+++ b/dom/media/FileBlockCache.h
@@ -45,17 +45,17 @@ namespace mozilla {
 // When WriteBlock() or MoveBlock() are called, data about how to complete
 // the block change is added to mBlockChanges, indexed by block index, and
 // the block index is appended to the mChangeIndexList. This enables
 // us to quickly tell if a block has been changed, and ensures we can perform
 // the changes in the correct order. An event is dispatched to perform the
 // changes listed in mBlockChanges to file. Read() checks mBlockChanges and
 // determines the current data to return, reading from file or from
 // mBlockChanges as necessary.
-class FileBlockCache : public nsRunnable {
+class FileBlockCache : public Runnable {
 public:
   enum {
     BLOCK_SIZE = MediaCacheStream::BLOCK_SIZE
   };
 
   FileBlockCache();
 
 protected:
--- a/dom/media/GraphDriver.cpp
+++ b/dom/media/GraphDriver.cpp
@@ -158,17 +158,17 @@ ThreadedDriver::ThreadedDriver(MediaStre
 { }
 
 ThreadedDriver::~ThreadedDriver()
 {
   if (mThread) {
     mThread->Shutdown();
   }
 }
-class MediaStreamGraphInitThreadRunnable : public nsRunnable {
+class MediaStreamGraphInitThreadRunnable : public Runnable {
 public:
   explicit MediaStreamGraphInitThreadRunnable(ThreadedDriver* aDriver)
     : mDriver(aDriver)
   {
   }
   NS_IMETHOD Run()
   {
     char aLocal;
@@ -400,17 +400,17 @@ void SystemClockDriver::WakeUp()
 
 OfflineClockDriver::OfflineClockDriver(MediaStreamGraphImpl* aGraphImpl, GraphTime aSlice)
   : ThreadedDriver(aGraphImpl),
     mSlice(aSlice)
 {
 
 }
 
-class MediaStreamGraphShutdownThreadRunnable : public nsRunnable {
+class MediaStreamGraphShutdownThreadRunnable : public Runnable {
 public:
   explicit MediaStreamGraphShutdownThreadRunnable(nsIThread* aThread)
     : mThread(aThread)
   {
   }
   NS_IMETHOD Run()
   {
     MOZ_ASSERT(NS_IsMainThread());
--- a/dom/media/GraphDriver.h
+++ b/dom/media/GraphDriver.h
@@ -523,17 +523,17 @@ private:
    * any thread safely. */
   Atomic<bool> mInCallback;
   /**
    * True if microphone is being used by this process. This is synchronized by
    * the graph's monitor. */
   bool mMicrophoneActive;
 };
 
-class AsyncCubebTask : public nsRunnable
+class AsyncCubebTask : public Runnable
 {
 public:
 
   AsyncCubebTask(AudioCallbackDriver* aDriver, AsyncCubebOperation aOperation);
 
   nsresult Dispatch(uint32_t aFlags = NS_DISPATCH_NORMAL)
   {
     nsresult rv = EnsureThread();
--- a/dom/media/Latency.cpp
+++ b/dom/media/Latency.cpp
@@ -39,17 +39,17 @@ static StaticRefPtr<AsyncLatencyLogger> 
 
 LogModule*
 GetLatencyLog()
 {
   static LazyLogModule sLog("MediaLatency");
   return sLog;
 }
 
-class LogEvent : public nsRunnable
+class LogEvent : public Runnable
 {
 public:
   LogEvent(AsyncLatencyLogger::LatencyLogIndex aIndex, uint64_t aID, int64_t aValue,
            TimeStamp aTimeStamp) :
     mIndex(aIndex),
     mID(aID),
     mValue(aValue),
     mTimeStamp(aTimeStamp)
--- a/dom/media/MediaCache.cpp
+++ b/dom/media/MediaCache.cpp
@@ -1371,17 +1371,17 @@ MediaCache::Update()
     MediaCache::ResourceStreamIterator iter(mSuspendedStatusToNotify[i]);
     while (MediaCacheStream* stream = iter.Next()) {
       stream->mClient->CacheClientNotifySuspendedStatusChanged();
     }
   }
   mSuspendedStatusToNotify.Clear();
 }
 
-class UpdateEvent : public nsRunnable
+class UpdateEvent : public Runnable
 {
 public:
   NS_IMETHOD Run()
   {
     if (gMediaCache) {
       gMediaCache->Update();
     }
     return NS_OK;
--- a/dom/media/MediaDecoderReader.cpp
+++ b/dom/media/MediaDecoderReader.cpp
@@ -219,17 +219,17 @@ MediaDecoderReader::AsyncReadMetadata()
     DECODER_WARN("ReadMetadata failed, rv=%x HasValidMedia=%d", rv, metadata->mInfo.HasValidMedia());
     return MetadataPromise::CreateAndReject(Reason::METADATA_ERROR, __func__);
   }
 
   // Success!
   return MetadataPromise::CreateAndResolve(metadata, __func__);
 }
 
-class ReRequestVideoWithSkipTask : public nsRunnable
+class ReRequestVideoWithSkipTask : public Runnable
 {
 public:
   ReRequestVideoWithSkipTask(MediaDecoderReader* aReader,
                              int64_t aTimeThreshold)
     : mReader(aReader)
     , mTimeThreshold(aTimeThreshold)
   {
   }
@@ -246,17 +246,17 @@ public:
     return NS_OK;
   }
 
 private:
   RefPtr<MediaDecoderReader> mReader;
   const int64_t mTimeThreshold;
 };
 
-class ReRequestAudioTask : public nsRunnable
+class ReRequestAudioTask : public Runnable
 {
 public:
   explicit ReRequestAudioTask(MediaDecoderReader* aReader)
     : mReader(aReader)
   {
   }
 
   NS_METHOD Run()
--- a/dom/media/MediaDecoderStateMachine.cpp
+++ b/dom/media/MediaDecoderStateMachine.cpp
@@ -360,17 +360,17 @@ MediaDecoderStateMachine::Initialization
 
 media::MediaSink*
 MediaDecoderStateMachine::CreateAudioSink()
 {
   RefPtr<MediaDecoderStateMachine> self = this;
   auto audioSinkCreator = [self] () {
     MOZ_ASSERT(self->OnTaskQueue());
     return new DecodedAudioDataSink(
-      self->mAudioQueue, self->GetMediaTime(),
+      self->mTaskQueue, self->mAudioQueue, self->GetMediaTime(),
       self->mInfo.mAudio, self->mAudioChannel);
   };
   return new AudioSinkWrapper(mTaskQueue, audioSinkCreator);
 }
 
 already_AddRefed<media::MediaSink>
 MediaDecoderStateMachine::CreateMediaSink(bool aAudioCaptured)
 {
--- a/dom/media/MediaEventSource.h
+++ b/dom/media/MediaEventSource.h
@@ -128,17 +128,17 @@ private:
  * copy when Move is possible or |Function| takes no arguments.
  */
 template<typename Target, typename Function>
 class ListenerHelper {
   // Define our custom runnable to minimize copy of the event data.
   // NS_NewRunnableFunction will result in 2 copies of the event data.
   // One is captured by the lambda and the other is the copy of the lambda.
   template <typename... Ts>
-  class R : public nsRunnable {
+  class R : public Runnable {
   public:
     template <typename... Us>
     R(RevocableToken* aToken, const Function& aFunction, Us&&... aEvents)
       : mToken(aToken)
       , mFunction(aFunction)
       , mEvents(Forward<Us>(aEvents)...) {}
 
     template <typename... Vs, size_t... Is>
--- a/dom/media/MediaFormatReader.cpp
+++ b/dom/media/MediaFormatReader.cpp
@@ -187,17 +187,17 @@ MediaFormatReader::Init()
     sSetupPrefCache = true;
     Preferences::AddBoolVarCache(&sIsEMEEnabled, "media.eme.enabled", false);
   }
 
   return NS_OK;
 }
 
 #ifdef MOZ_EME
-class DispatchKeyNeededEvent : public nsRunnable {
+class DispatchKeyNeededEvent : public Runnable {
 public:
   DispatchKeyNeededEvent(AbstractMediaDecoder* aDecoder,
                          nsTArray<uint8_t>& aInitData,
                          const nsString& aInitDataType)
     : mDecoder(aDecoder)
     , mInitData(aInitData)
     , mInitDataType(aInitDataType)
   {
--- a/dom/media/MediaManager.cpp
+++ b/dom/media/MediaManager.cpp
@@ -393,17 +393,17 @@ private:
 };
 
 /**
  * Send an error back to content.
  * Do this only on the main thread. The onSuccess callback is also passed here
  * so it can be released correctly.
  */
 template<class SuccessCallbackType>
-class ErrorCallbackRunnable : public nsRunnable
+class ErrorCallbackRunnable : public Runnable
 {
 public:
   ErrorCallbackRunnable(
     nsCOMPtr<SuccessCallbackType>& aOnSuccess,
     nsCOMPtr<nsIDOMGetUserMediaErrorCallback>& aOnFailure,
     MediaMgrError& aError,
     uint64_t aWindowID)
     : mError(&aError)
@@ -444,17 +444,17 @@ private:
   nsCOMPtr<SuccessCallbackType> mOnSuccess;
   nsCOMPtr<nsIDOMGetUserMediaErrorCallback> mOnFailure;
   RefPtr<MediaMgrError> mError;
   uint64_t mWindowID;
   RefPtr<MediaManager> mManager; // get ref to this when creating the runnable
 };
 
 // Handle removing GetUserMediaCallbackMediaStreamListener from main thread
-class GetUserMediaListenerRemove: public nsRunnable
+class GetUserMediaListenerRemove: public Runnable
 {
 public:
   GetUserMediaListenerRemove(uint64_t aWindowID,
     GetUserMediaCallbackMediaStreamListener *aListener)
     : mWindowID(aWindowID)
     , mListener(aListener) {}
 
   NS_IMETHOD
@@ -729,17 +729,17 @@ NS_IMPL_CYCLE_COLLECTION_INHERITED(FakeT
  *
  * Note that the various GetUserMedia Runnable classes currently allow for
  * two streams.  If we ever need to support getting more than two streams
  * at once, we could convert everything to nsTArray<RefPtr<blah> >'s,
  * though that would complicate the constructors some.  Currently the
  * GetUserMedia spec does not allow for more than 2 streams to be obtained in
  * one call, to simplify handling of constraints.
  */
-class GetUserMediaStreamRunnable : public nsRunnable
+class GetUserMediaStreamRunnable : public Runnable
 {
 public:
   GetUserMediaStreamRunnable(
     nsCOMPtr<nsIDOMGetUserMediaSuccessCallback>& aOnSuccess,
     nsCOMPtr<nsIDOMGetUserMediaErrorCallback>& aOnFailure,
     uint64_t aWindowID,
     GetUserMediaCallbackMediaStreamListener* aListener,
     const nsCString& aOrigin,
@@ -1290,17 +1290,17 @@ private:
   bool mDeviceChosen;
 public:
   nsAutoPtr<MediaManager::SourceSet> mSourceSet;
 private:
   RefPtr<MediaManager> mManager; // get ref to this when creating the runnable
 };
 
 #if defined(ANDROID) && !defined(MOZ_WIDGET_GONK)
-class GetUserMediaRunnableWrapper : public nsRunnable
+class GetUserMediaRunnableWrapper : public Runnable
 {
 public:
   // This object must take ownership of task
   GetUserMediaRunnableWrapper(GetUserMediaTask* task) :
     mTask(task) {
   }
 
   ~GetUserMediaRunnableWrapper() {
@@ -2615,17 +2615,17 @@ MediaManager::Shutdown()
 
   // Because mMediaThread is not an nsThread, we must dispatch to it so it can
   // clean up BackgroundChild. Continue stopping thread once this is done.
 
   class ShutdownTask : public Task
   {
   public:
     ShutdownTask(MediaManager* aManager,
-                 nsRunnable* aReply)
+                 Runnable* aReply)
       : mManager(aManager)
       , mReply(aReply) {}
   private:
     void
     Run() override
     {
       LOG(("MediaManager Thread Shutdown"));
       MOZ_ASSERT(MediaManager::IsInMediaThread());
@@ -2639,17 +2639,17 @@ MediaManager::Shutdown()
       // must explicitly do this before dispatching the reply, since the reply may kill us with Stop()
       mManager->mBackend = nullptr; // last reference, will invoke Shutdown() again
 
       if (NS_FAILED(NS_DispatchToMainThread(mReply.forget()))) {
         LOG(("Will leak thread: DispatchToMainthread of reply runnable failed in MediaManager shutdown"));
       }
     }
     RefPtr<MediaManager> mManager;
-    RefPtr<nsRunnable> mReply;
+    RefPtr<Runnable> mReply;
   };
 
   // Post ShutdownTask to execute on mMediaThread and pass in a lambda
   // callback to be executed back on this thread once it is done.
   //
   // The lambda callback "captures" the 'this' pointer for member access.
   // This is safe since this is guaranteed to be here since sSingleton isn't
   // cleared until the lambda function clears it.
--- a/dom/media/MediaManager.h
+++ b/dom/media/MediaManager.h
@@ -334,17 +334,17 @@ private:
 
   // Accessed from MediaStreamGraph thread, MediaManager thread, and MainThread
   // No locking needed as they're only addrefed except on the MediaManager thread
   RefPtr<AudioDevice> mAudioDevice; // threadsafe refcnt
   RefPtr<VideoDevice> mVideoDevice; // threadsafe refcnt
   RefPtr<SourceMediaStream> mStream; // threadsafe refcnt
 };
 
-class GetUserMediaNotificationEvent: public nsRunnable
+class GetUserMediaNotificationEvent: public Runnable
 {
   public:
     enum GetUserMediaStatus {
       STARTING,
       STOPPING,
       STOPPED_TRACK,
     };
     GetUserMediaNotificationEvent(GetUserMediaCallbackMediaStreamListener* aListener,
@@ -384,17 +384,17 @@ typedef enum {
   MEDIA_STOP,
   MEDIA_STOP_TRACK,
   MEDIA_DIRECT_LISTENERS,
 } MediaOperation;
 
 class MediaManager;
 class GetUserMediaTask;
 
-class ReleaseMediaOperationResource : public nsRunnable
+class ReleaseMediaOperationResource : public Runnable
 {
 public:
   ReleaseMediaOperationResource(already_AddRefed<DOMMediaStream> aStream,
     OnTracksAvailableCallback* aOnTracksAvailableCallback):
     mStream(aStream),
     mOnTracksAvailableCallback(aOnTracksAvailableCallback) {}
   NS_IMETHOD Run() override {return NS_OK;}
 private:
--- a/dom/media/MediaQueue.h
+++ b/dom/media/MediaQueue.h
@@ -31,17 +31,17 @@ public:
       mReentrantMonitor("mediaqueue"),
       mEndOfStream(false)
   {}
 
   ~MediaQueue() {
     Reset();
   }
 
-  inline size_t GetSize() {
+  inline size_t GetSize() const {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     return nsDeque::GetSize();
   }
 
   inline void Push(T* aItem) {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     MOZ_ASSERT(aItem);
     NS_ADDREF(aItem);
@@ -60,43 +60,43 @@ public:
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     RefPtr<T> rv = dont_AddRef(static_cast<T*>(nsDeque::PopFront()));
     if (rv) {
       mPopEvent.Notify(rv);
     }
     return rv.forget();
   }
 
-  inline RefPtr<T> Peek() {
+  inline RefPtr<T> Peek() const {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     return static_cast<T*>(nsDeque::Peek());
   }
 
-  inline RefPtr<T> PeekFront() {
+  inline RefPtr<T> PeekFront() const {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     return static_cast<T*>(nsDeque::PeekFront());
   }
 
   void Reset() {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     while (GetSize() > 0) {
       RefPtr<T> x = dont_AddRef(static_cast<T*>(nsDeque::PopFront()));
     }
     mEndOfStream = false;
   }
 
-  bool AtEndOfStream() {
+  bool AtEndOfStream() const {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     return GetSize() == 0 && mEndOfStream;
   }
 
   // Returns true if the media queue has had its last item added to it.
   // This happens when the media stream has been completely decoded. Note this
   // does not mean that the corresponding stream has finished playback.
-  bool IsFinished() {
+  bool IsFinished() const {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     return mEndOfStream;
   }
 
   // Informs the media queue that it won't be receiving any more items.
   void Finish() {
     ReentrantMonitorAutoEnter mon(mReentrantMonitor);
     mEndOfStream = true;
--- a/dom/media/MediaRecorder.cpp
+++ b/dom/media/MediaRecorder.cpp
@@ -161,17 +161,17 @@ NS_IMPL_RELEASE_INHERITED(MediaRecorder,
 class MediaRecorder::Session: public nsIObserver,
                               public PrincipalChangeObserver<MediaStreamTrack>,
                               public DOMMediaStream::TrackListener
 {
   NS_DECL_THREADSAFE_ISUPPORTS
 
   // Main thread task.
   // Create a blob event and send back to client.
-  class PushBlobRunnable : public nsRunnable
+  class PushBlobRunnable : public Runnable
   {
   public:
     explicit PushBlobRunnable(Session* aSession)
       : mSession(aSession)
     { }
 
     NS_IMETHODIMP Run()
     {
@@ -191,17 +191,17 @@ class MediaRecorder::Session: public nsI
       return NS_OK;
     }
 
   private:
     RefPtr<Session> mSession;
   };
 
   // Notify encoder error, run in main thread task. (Bug 1095381)
-  class EncoderErrorNotifierRunnable : public nsRunnable
+  class EncoderErrorNotifierRunnable : public Runnable
   {
   public:
     explicit EncoderErrorNotifierRunnable(Session* aSession)
       : mSession(aSession)
     { }
 
     NS_IMETHODIMP Run()
     {
@@ -219,17 +219,17 @@ class MediaRecorder::Session: public nsI
       return NS_OK;
     }
 
   private:
     RefPtr<Session> mSession;
   };
 
   // Fire start event and set mimeType, run in main thread task.
-  class DispatchStartEventRunnable : public nsRunnable
+  class DispatchStartEventRunnable : public Runnable
   {
   public:
     DispatchStartEventRunnable(Session* aSession, const nsAString & aEventName)
       : mSession(aSession)
       , mEventName(aEventName)
     { }
 
     NS_IMETHODIMP Run()
@@ -248,17 +248,17 @@ class MediaRecorder::Session: public nsI
 
   private:
     RefPtr<Session> mSession;
     nsString mEventName;
   };
 
   // Record thread task and it run in Media Encoder thread.
   // Fetch encoded Audio/Video data from MediaEncoder.
-  class ExtractRunnable : public nsRunnable
+  class ExtractRunnable : public Runnable
   {
   public:
     explicit ExtractRunnable(Session* aSession)
       : mSession(aSession) {}
 
     ~ExtractRunnable()
     {}
 
@@ -348,17 +348,17 @@ class MediaRecorder::Session: public nsI
       LOG(LogLevel::Debug, ("Session.NotifyTracksAvailable track type = (%d)", trackTypes));
       mSession->InitEncoder(trackTypes);
     }
   private:
     RefPtr<Session> mSession;
   };
   // Main thread task.
   // To delete RecordingSession object.
-  class DestroyRunnable : public nsRunnable
+  class DestroyRunnable : public Runnable
   {
   public:
     explicit DestroyRunnable(Session* aSession)
       : mSession(aSession) {}
 
     NS_IMETHODIMP Run()
     {
       LOG(LogLevel::Debug, ("Session.DestroyRunnable session refcnt = (%d) stopIssued %d s=(%p)",
--- a/dom/media/MediaStreamGraph.cpp
+++ b/dom/media/MediaStreamGraph.cpp
@@ -888,17 +888,17 @@ SetImageToBlackPixel(PlanarYCbCrImage* a
   data.mYChannel = blackPixel;
   data.mCbChannel = blackPixel + 1;
   data.mCrChannel = blackPixel + 2;
   data.mYStride = data.mCbCrStride = 1;
   data.mPicSize = data.mYSize = data.mCbCrSize = IntSize(1, 1);
   aImage->CopyData(data);
 }
 
-class VideoFrameContainerInvalidateRunnable : public nsRunnable {
+class VideoFrameContainerInvalidateRunnable : public Runnable {
 public:
   explicit VideoFrameContainerInvalidateRunnable(VideoFrameContainer* aVideoFrameContainer)
     : mVideoFrameContainer(aVideoFrameContainer)
   {}
   NS_IMETHOD Run()
   {
     MOZ_ASSERT(NS_IsMainThread());
 
@@ -1588,17 +1588,17 @@ MediaStreamGraphImpl::ForceShutDown(Shut
     EnsureNextIterationLocked();
   }
 }
 
 /* static */ StaticRefPtr<nsIAsyncShutdownBlocker> gMediaStreamGraphShutdownBlocker;
 
 namespace {
 
-class MediaStreamGraphShutDownRunnable : public nsRunnable {
+class MediaStreamGraphShutDownRunnable : public Runnable {
 public:
   explicit MediaStreamGraphShutDownRunnable(MediaStreamGraphImpl* aGraph)
     : mGraph(aGraph)
   {}
   NS_IMETHOD Run()
   {
     NS_ASSERTION(mGraph->mDetectedNotRunning,
                  "We should know the graph thread control loop isn't running!");
@@ -1648,17 +1648,17 @@ public:
         MediaStreamGraphImpl::LIFECYCLE_WAITING_FOR_STREAM_DESTRUCTION;
     }
     return NS_OK;
   }
 private:
   RefPtr<MediaStreamGraphImpl> mGraph;
 };
 
-class MediaStreamGraphStableStateRunnable : public nsRunnable {
+class MediaStreamGraphStableStateRunnable : public Runnable {
 public:
   explicit MediaStreamGraphStableStateRunnable(MediaStreamGraphImpl* aGraph,
                                                bool aSourceIsMSG)
     : mGraph(aGraph)
     , mSourceIsMSG(aSourceIsMSG)
   {
   }
   NS_IMETHOD Run()
@@ -2580,17 +2580,17 @@ MediaStream::AddMainThreadListener(MainT
 
   mMainThreadListeners.AppendElement(aListener);
 
   // If it is not yet time to send the notification, then finish here.
   if (!mFinishedNotificationSent) {
     return;
   }
 
-  class NotifyRunnable final : public nsRunnable
+  class NotifyRunnable final : public Runnable
   {
   public:
     explicit NotifyRunnable(MediaStream* aStream)
       : mStream(aStream)
     {}
 
     NS_IMETHOD Run() override
     {
@@ -2600,17 +2600,17 @@ MediaStream::AddMainThreadListener(MainT
     }
 
   private:
     ~NotifyRunnable() {}
 
     RefPtr<MediaStream> mStream;
   };
 
-  RefPtr<nsRunnable> runnable = new NotifyRunnable(this);
+  nsCOMPtr<nsIRunnable> runnable = new NotifyRunnable(this);
   NS_WARN_IF(NS_FAILED(NS_DispatchToMainThread(runnable.forget())));
 }
 
 nsresult
 SourceMediaStream::OpenAudioInput(int aID,
                                   AudioDataListener *aListener)
 {
   if (GraphImpl()) {
@@ -3472,17 +3472,17 @@ void
 MediaStreamGraph::AddStream(MediaStream* aStream)
 {
   NS_ADDREF(aStream);
   MediaStreamGraphImpl* graph = static_cast<MediaStreamGraphImpl*>(this);
   aStream->SetGraphImpl(graph);
   graph->AppendMessage(MakeUnique<CreateMessage>(aStream));
 }
 
-class GraphStartedRunnable final : public nsRunnable
+class GraphStartedRunnable final : public Runnable
 {
 public:
   GraphStartedRunnable(AudioNodeStream* aStream, MediaStreamGraph* aGraph)
   : mStream(aStream)
   , mGraph(aGraph)
   { }
 
   NS_IMETHOD Run() {
--- a/dom/media/TextTrackList.cpp
+++ b/dom/media/TextTrackList.cpp
@@ -131,17 +131,17 @@ TextTrackList::RemoveTextTrack(TextTrack
 void
 TextTrackList::DidSeek()
 {
   for (uint32_t i = 0; i < mTextTracks.Length(); i++) {
     mTextTracks[i]->SetDirty();
   }
 }
 
-class TrackEventRunner final: public nsRunnable
+class TrackEventRunner final: public Runnable
 {
 public:
   TrackEventRunner(TextTrackList* aList, nsIDOMEvent* aEvent)
     : mList(aList)
     , mEvent(aEvent)
   {}
 
   NS_IMETHOD Run() override
--- a/dom/media/VideoUtils.cpp
+++ b/dom/media/VideoUtils.cpp
@@ -26,20 +26,20 @@
 #include "nsContentTypeParser.h"
 
 #include <stdint.h>
 
 namespace mozilla {
 
 using layers::PlanarYCbCrImage;
 
-static inline CheckedInt64 SaferMultDiv(int64_t aValue, uint32_t aMul, uint32_t aDiv) {
+CheckedInt64 SaferMultDiv(int64_t aValue, uint32_t aMul, uint32_t aDiv) {
   int64_t major = aValue / aDiv;
   int64_t remainder = aValue % aDiv;
-  return CheckedInt64(remainder) * aMul / aDiv + major * aMul;
+  return CheckedInt64(remainder) * aMul / aDiv + CheckedInt64(major) * aMul;
 }
 
 // Converts from number of audio frames to microseconds, given the specified
 // audio rate.
 CheckedInt64 FramesToUsecs(int64_t aFrames, uint32_t aRate) {
   return SaferMultDiv(aFrames, USECS_PER_S, aRate);
 }
 
--- a/dom/media/VideoUtils.h
+++ b/dom/media/VideoUtils.h
@@ -74,32 +74,32 @@ private:
   ReentrantMonitorConditionallyEnter& operator =(const ReentrantMonitorConditionallyEnter&);
   static void* operator new(size_t) CPP_THROW_NEW;
   static void operator delete(void*);
 
   ReentrantMonitor* mReentrantMonitor;
 };
 
 // Shuts down a thread asynchronously.
-class ShutdownThreadEvent : public nsRunnable
+class ShutdownThreadEvent : public Runnable
 {
 public:
   explicit ShutdownThreadEvent(nsIThread* aThread) : mThread(aThread) {}
   ~ShutdownThreadEvent() {}
   NS_IMETHOD Run() override {
     mThread->Shutdown();
     mThread = nullptr;
     return NS_OK;
   }
 private:
   nsCOMPtr<nsIThread> mThread;
 };
 
 template<class T>
-class DeleteObjectTask: public nsRunnable {
+class DeleteObjectTask: public Runnable {
 public:
   explicit DeleteObjectTask(nsAutoPtr<T>& aObject)
     : mObject(aObject)
   {
   }
   NS_IMETHOD Run() {
     NS_ASSERTION(NS_IsMainThread(), "Must be on main thread.");
     mObject = nullptr;
@@ -126,16 +126,19 @@ media::TimeIntervals GetEstimatedBuffere
                                                     int64_t aDurationUsecs);
 
 // Converts from number of audio frames (aFrames) to microseconds, given
 // the specified audio rate (aRate).
 CheckedInt64 FramesToUsecs(int64_t aFrames, uint32_t aRate);
 // Converts from number of audio frames (aFrames) TimeUnit, given
 // the specified audio rate (aRate).
 media::TimeUnit FramesToTimeUnit(int64_t aFrames, uint32_t aRate);
+// Perform aValue * aMul / aDiv, reducing the possibility of overflow due to
+// aValue * aMul overflowing.
+CheckedInt64 SaferMultDiv(int64_t aValue, uint32_t aMul, uint32_t aDiv);
 
 // Converts from microseconds (aUsecs) to number of audio frames, given the
 // specified audio rate (aRate). Stores the result in aOutFrames. Returns
 // true if the operation succeeded, or false if there was an integer
 // overflow while calulating the conversion.
 CheckedInt64 UsecsToFrames(int64_t aUsecs, uint32_t aRate);
 
 // Format TimeUnit as number of frames at given rate.
--- a/dom/media/android/AndroidMediaPluginHost.cpp
+++ b/dom/media/android/AndroidMediaPluginHost.cpp
@@ -37,17 +37,17 @@ Decoder::Decoder() :
 
 namespace mozilla {
 
 static char* GetResource(Decoder *aDecoder)
 {
   return static_cast<char*>(aDecoder->mResource);
 }
 
-class GetIntPrefEvent : public nsRunnable {
+class GetIntPrefEvent : public Runnable {
 public:
   GetIntPrefEvent(const char* aPref, int32_t* aResult)
     : mPref(aPref), mResult(aResult) {}
   NS_IMETHOD Run() {
     return Preferences::GetInt(mPref, mResult);
   }
 private:
   const char* mPref;
--- a/dom/media/android/AndroidMediaResourceServer.cpp
+++ b/dom/media/android/AndroidMediaResourceServer.cpp
@@ -101,17 +101,17 @@ ReadCRLF (StreamType* aStream, nsLineBuf
   }
 }
 
 // Each client HTTP request results in a thread being spawned to process it.
 // That thread has a single event dispatched to it which handles the HTTP
 // protocol. It parses the headers and forwards data from the MediaResource
 // associated with the URL back to client. When the request is complete it will
 // shutdown the thread.
-class ServeResourceEvent : public nsRunnable {
+class ServeResourceEvent : public Runnable {
 private:
   // Reading from this reads the data sent from the client.
   nsCOMPtr<nsIInputStream> mInput;
 
   // Writing to this sends data to the client.
   nsCOMPtr<nsIOutputStream> mOutput;
 
   // The AndroidMediaResourceServer that owns the MediaResource instances
--- a/dom/media/android/AndroidMediaResourceServer.h
+++ b/dom/media/android/AndroidMediaResourceServer.h
@@ -32,17 +32,17 @@ class MediaResource;
   Gecko network requests and media cache usage.
 
   The AndroidMediaResourceServer can be instantiated on any thread and
   its methods are threadsafe - they can be called on any thread.
   The server socket itself is always run on the main thread and
   this is done by the Start() static method by synchronously
   dispatching to the main thread.
 */
-class AndroidMediaResourceServer : public nsRunnable
+class AndroidMediaResourceServer : public Runnable
 {
 private:
   // Mutex protecting private members of AndroidMediaResourceServer.
   // All member variables below this point in the class definition
   // must acquire the mutex before access.
   mozilla::Mutex mMutex;
 
   // Server socket used to listen for incoming connections
--- a/dom/media/eme/CDMCallbackProxy.cpp
+++ b/dom/media/eme/CDMCallbackProxy.cpp
@@ -18,17 +18,17 @@
 namespace mozilla {
 
 CDMCallbackProxy::CDMCallbackProxy(CDMProxy* aProxy)
   : mProxy(aProxy)
 {
 
 }
 
-class SetSessionIdTask : public nsRunnable {
+class SetSessionIdTask : public Runnable {
 public:
   SetSessionIdTask(CDMProxy* aProxy,
                    uint32_t aToken,
                    const nsCString& aSessionId)
     : mProxy(aProxy)
     , mToken(aToken)
     , mSid(NS_ConvertUTF8toUTF16(aSessionId))
   {
@@ -51,17 +51,17 @@ CDMCallbackProxy::SetSessionId(uint32_t 
   MOZ_ASSERT(mProxy->IsOnGMPThread());
 
   nsCOMPtr<nsIRunnable> task(new SetSessionIdTask(mProxy,
                                                   aToken,
                                                   aSessionId));
   NS_DispatchToMainThread(task);
 }
 
-class LoadSessionTask : public nsRunnable {
+class LoadSessionTask : public Runnable {
 public:
   LoadSessionTask(CDMProxy* aProxy,
                   uint32_t aPromiseId,
                   bool aSuccess)
     : mProxy(aProxy)
     , mPid(aPromiseId)
     , mSuccess(aSuccess)
   {
@@ -92,17 +92,17 @@ void
 CDMCallbackProxy::ResolvePromise(uint32_t aPromiseId)
 {
   MOZ_ASSERT(mProxy->IsOnGMPThread());
 
   // Note: CDMProxy proxies this from non-main threads to main thread.
   mProxy->ResolvePromise(aPromiseId);
 }
 
-class RejectPromiseTask : public nsRunnable {
+class RejectPromiseTask : public Runnable {
 public:
   RejectPromiseTask(CDMProxy* aProxy,
                     uint32_t aPromiseId,
                     nsresult aException,
                     const nsCString& aMessage)
     : mProxy(aProxy)
     , mPid(aPromiseId)
     , mException(aException)
@@ -132,17 +132,17 @@ CDMCallbackProxy::RejectPromise(uint32_t
   nsCOMPtr<nsIRunnable> task;
   task = new RejectPromiseTask(mProxy,
                                aPromiseId,
                                aException,
                                aMessage);
   NS_DispatchToMainThread(task);
 }
 
-class SessionMessageTask : public nsRunnable {
+class SessionMessageTask : public Runnable {
 public:
   SessionMessageTask(CDMProxy* aProxy,
                      const nsCString& aSessionId,
                      GMPSessionMessageType aMessageType,
                      const nsTArray<uint8_t>& aMessage)
     : mProxy(aProxy)
     , mSid(NS_ConvertUTF8toUTF16(aSessionId))
     , mMsgType(aMessageType)
@@ -172,17 +172,17 @@ CDMCallbackProxy::SessionMessage(const n
   nsCOMPtr<nsIRunnable> task;
   task = new SessionMessageTask(mProxy,
                                 aSessionId,
                                 aMessageType,
                                 aMessage);
   NS_DispatchToMainThread(task);
 }
 
-class ExpirationChangeTask : public nsRunnable {
+class ExpirationChangeTask : public Runnable {
 public:
   ExpirationChangeTask(CDMProxy* aProxy,
                        const nsCString& aSessionId,
                        GMPTimestamp aExpiryTime)
     : mProxy(aProxy)
     , mSid(NS_ConvertUTF8toUTF16(aSessionId))
     , mTimestamp(aExpiryTime)
   {}
@@ -230,17 +230,17 @@ CDMCallbackProxy::SessionClosed(const ns
 
   nsCOMPtr<nsIRunnable> task;
   task = NS_NewRunnableMethodWithArg<nsString>(mProxy,
                                                &CDMProxy::OnSessionClosed,
                                                NS_ConvertUTF8toUTF16(aSessionId));
   NS_DispatchToMainThread(task);
 }
 
-class SessionErrorTask : public nsRunnable {
+class SessionErrorTask : public Runnable {
 public:
   SessionErrorTask(CDMProxy* aProxy,
                    const nsCString& aSessionId,
                    nsresult aException,
                    uint32_t aSystemCode,
                    const nsCString& aMessage)
     : mProxy(aProxy)
     , mSid(NS_ConvertUTF8toUTF16(aSessionId))
--- a/dom/media/eme/CDMProxy.h
+++ b/dom/media/eme/CDMProxy.h
@@ -263,17 +263,17 @@ private:
     RefPtr<MediaRawData> mSample;
   private:
     ~DecryptJob() {}
     MozPromiseHolder<DecryptPromise> mPromise;
   };
   // GMP thread only.
   void gmp_Decrypt(RefPtr<DecryptJob> aJob);
 
-  class RejectPromiseTask : public nsRunnable {
+  class RejectPromiseTask : public Runnable {
   public:
     RejectPromiseTask(CDMProxy* aProxy,
                       PromiseId aId,
                       nsresult aCode,
                       const nsCString& aReason)
       : mProxy(aProxy)
       , mId(aId)
       , mCode(aCode)
--- a/dom/media/gmp/GMPContentParent.cpp
+++ b/dom/media/gmp/GMPContentParent.cpp
@@ -42,17 +42,17 @@ GMPContentParent::GMPContentParent(GMPPa
 }
 
 GMPContentParent::~GMPContentParent()
 {
   XRE_GetIOMessageLoop()->PostTask(FROM_HERE,
                                    new DeleteTask<Transport>(GetTransport()));
 }
 
-class ReleaseGMPContentParent : public nsRunnable
+class ReleaseGMPContentParent : public Runnable
 {
 public:
   explicit ReleaseGMPContentParent(GMPContentParent* aToRelease)
     : mToRelease(aToRelease)
   {
   }
 
   NS_IMETHOD Run()
--- a/dom/media/gmp/GMPParent.cpp
+++ b/dom/media/gmp/GMPParent.cpp
@@ -467,17 +467,17 @@ GMPParent::Shutdown()
   // Bug 1043671 is fixed
   if (!mDeleteProcessOnlyOnUnload) {
     // Destroy ourselves and rise from the fire to save memory
     mService->ReAddOnGMPThread(self);
   } // else we've been asked to die and stay dead
   MOZ_ASSERT(mState == GMPStateNotLoaded);
 }
 
-class NotifyGMPShutdownTask : public nsRunnable {
+class NotifyGMPShutdownTask : public Runnable {
 public:
   explicit NotifyGMPShutdownTask(const nsAString& aNodeId)
     : mNodeId(aNodeId)
   {
   }
   NS_IMETHOD Run() {
     MOZ_ASSERT(NS_IsMainThread());
     nsCOMPtr<nsIObserverService> obsService = mozilla::services::GetObserverService();
@@ -1042,17 +1042,17 @@ GMPParent::RecvAsyncShutdownComplete()
     mService->SetAsyncShutdownPluginState(this, 'L',
       NS_LITERAL_CSTRING("Received AsyncShutdownComplete"));
   }
 #endif
   AbortAsyncShutdown();
   return true;
 }
 
-class RunCreateContentParentCallbacks : public nsRunnable
+class RunCreateContentParentCallbacks : public Runnable
 {
 public:
   explicit RunCreateContentParentCallbacks(GMPContentParent* aGMPContentParent)
     : mGMPContentParent(aGMPContentParent)
   {
   }
 
   void TakeCallbacks(nsTArray<UniquePtr<GetGMPContentParentCallback>>& aCallbacks)
--- a/dom/media/gmp/GMPService.cpp
+++ b/dom/media/gmp/GMPService.cpp
@@ -60,17 +60,17 @@ GetGMPLog()
 #undef __CLASS__
 #endif
 #define __CLASS__ "GMPService"
 
 namespace gmp {
 
 static StaticRefPtr<GeckoMediaPluginService> sSingletonService;
 
-class GMPServiceCreateHelper final : public nsRunnable
+class GMPServiceCreateHelper final : public mozilla::Runnable
 {
   RefPtr<GeckoMediaPluginService> mService;
 
 public:
   static already_AddRefed<GeckoMediaPluginService>
   GetOrCreate()
   {
     RefPtr<GeckoMediaPluginService> service;
--- a/dom/media/gmp/GMPServiceChild.cpp
+++ b/dom/media/gmp/GMPServiceChild.cpp
@@ -299,17 +299,17 @@ GMPServiceChild::GetAlreadyBridgedTo(nsT
 {
   aAlreadyBridgedTo.SetCapacity(mContentParents.Count());
   for (auto iter = mContentParents.Iter(); !iter.Done(); iter.Next()) {
     const uint64_t& id = iter.Key();
     aAlreadyBridgedTo.AppendElement(id);
   }
 }
 
-class OpenPGMPServiceChild : public nsRunnable
+class OpenPGMPServiceChild : public mozilla::Runnable
 {
 public:
   OpenPGMPServiceChild(UniquePtr<GMPServiceChild>&& aGMPServiceChild,
                        mozilla::ipc::Transport* aTransport,
                        base::ProcessId aOtherPid)
     : mGMPServiceChild(Move(aGMPServiceChild)),
       mTransport(aTransport),
       mOtherPid(aOtherPid)
--- a/dom/media/gmp/GMPServiceParent.cpp
+++ b/dom/media/gmp/GMPServiceParent.cpp
@@ -777,17 +777,17 @@ GeckoMediaPluginServiceParent::LoadFromE
     }
   }
 
   mScannedPluginOnDisk = true;
   RefPtr<AbstractThread> thread(GetAbstractGMPThread());
   return GenericPromise::All(thread, promises);
 }
 
-class NotifyObserversTask final : public nsRunnable {
+class NotifyObserversTask final : public mozilla::Runnable {
 public:
   explicit NotifyObserversTask(const char* aTopic, nsString aData = EmptyString())
     : mTopic(aTopic)
     , mData(aData)
   {}
   NS_IMETHOD Run() override {
     MOZ_ASSERT(NS_IsMainThread());
     nsCOMPtr<nsIObserverService> obsService = mozilla::services::GetObserverService();
@@ -873,21 +873,16 @@ GeckoMediaPluginServiceParent::RemoveAnd
 {
   MOZ_ASSERT(NS_IsMainThread());
   return GMPDispatch(
     new PathRunnable(this, aDirectory,
                      PathRunnable::EOperation::REMOVE_AND_DELETE_FROM_DISK,
                      aDefer));
 }
 
-class DummyRunnable : public nsRunnable {
-public:
-  NS_IMETHOD Run() { return NS_OK; }
-};
-
 NS_IMETHODIMP
 GeckoMediaPluginServiceParent::GetPluginVersionForAPI(const nsACString& aAPI,
                                                       nsTArray<nsCString>* aTags,
                                                       bool* aHasPlugin,
                                                       nsACString& aOutVersion)
 {
   NS_ENSURE_ARG(aTags && aTags->Length() > 0);
   NS_ENSURE_ARG(aHasPlugin);
@@ -928,17 +923,17 @@ GeckoMediaPluginServiceParent::EnsurePlu
   const char* env = nullptr;
   if (!mScannedPluginOnDisk && (env = PR_GetEnv("MOZ_GMP_PATH")) && *env) {
     // We have a MOZ_GMP_PATH environment variable which may specify the
     // location of plugins to load, and we haven't yet scanned the disk to
     // see if there are plugins there. Get the GMP thread, which will
     // cause an event to be dispatched to which scans for plugins. We
     // dispatch a sync event to the GMP thread here in order to wait until
     // after the GMP thread has scanned any paths in MOZ_GMP_PATH.
-    nsresult rv = GMPDispatch(new DummyRunnable(), NS_DISPATCH_SYNC);
+    nsresult rv = GMPDispatch(new mozilla::Runnable(), NS_DISPATCH_SYNC);
     NS_ENSURE_SUCCESS(rv, rv);
     MOZ_ASSERT(mScannedPluginOnDisk, "Should have scanned MOZ_GMP_PATH by now");
   }
 
   return NS_OK;
 }
 
 GMPParent*
@@ -1828,17 +1823,17 @@ GMPServiceParent::RecvGetGMPPluginVersio
 {
   RefPtr<GeckoMediaPluginServiceParent> service =
     GeckoMediaPluginServiceParent::GetSingleton();
   return service &&
          NS_SUCCEEDED(service->GetPluginVersionForAPI(aAPI, &aTags, aHasPlugin,
                                                       *aVersion));
 }
 
-class DeleteGMPServiceParent : public nsRunnable
+class DeleteGMPServiceParent : public mozilla::Runnable
 {
 public:
   explicit DeleteGMPServiceParent(GMPServiceParent* aToDelete)
     : mToDelete(aToDelete)
   {
   }
 
   NS_IMETHODIMP Run()
@@ -1851,17 +1846,17 @@ private:
 };
 
 void
 GMPServiceParent::ActorDestroy(ActorDestroyReason aWhy)
 {
   NS_DispatchToCurrentThread(new DeleteGMPServiceParent(this));
 }
 
-class OpenPGMPServiceParent : public nsRunnable
+class OpenPGMPServiceParent : public mozilla::Runnable
 {
 public:
   OpenPGMPServiceParent(GMPServiceParent* aGMPServiceParent,
                         mozilla::ipc::Transport* aTransport,
                         base::ProcessId aOtherPid,
                         bool* aResult)
     : mGMPServiceParent(aGMPServiceParent),
       mTransport(aTransport),
--- a/dom/media/gmp/GMPServiceParent.h
+++ b/dom/media/gmp/GMPServiceParent.h
@@ -113,17 +113,17 @@ protected:
                             const nsTArray<nsCString>& aTags,
                             UniquePtr<GetGMPContentParentCallback>&& aCallback)
     override;
 private:
   GMPParent* ClonePlugin(const GMPParent* aOriginal);
   nsresult EnsurePluginsOnDiskScanned();
   nsresult InitStorage();
 
-  class PathRunnable : public nsRunnable
+  class PathRunnable : public Runnable
   {
   public:
     enum EOperation {
       REMOVE,
       REMOVE_AND_DELETE_FROM_DISK,
     };
 
     PathRunnable(GeckoMediaPluginServiceParent* aService, const nsAString& aPath,
--- a/dom/media/gtest/TestGMPCrossOrigin.cpp
+++ b/dom/media/gtest/TestGMPCrossOrigin.cpp
@@ -346,17 +346,17 @@ private:
   virtual ~GMPShutdownObserver() {}
   nsCOMPtr<nsIRunnable> mShutdownTask;
   nsCOMPtr<nsIRunnable> mContinuation;
   const nsString mNodeId;
 };
 
 NS_IMPL_ISUPPORTS(GMPShutdownObserver, nsIRunnable, nsIObserver)
 
-class NotifyObserversTask : public nsRunnable {
+class NotifyObserversTask : public Runnable {
 public:
   explicit NotifyObserversTask(const char* aTopic)
     : mTopic(aTopic)
   {}
   NS_IMETHOD Run() {
     MOZ_ASSERT(NS_IsMainThread());
     nsCOMPtr<nsIObserverService> observerService =
         mozilla::services::GetObserverService();
@@ -616,17 +616,17 @@ class GMPStorageTest : public GMPDecrypt
                        const nsAString& aTopLevelOrigin,
                        bool aInPBMode,
                        const nsCString& aUpdate)
   {
     nsTArray<nsCString> updates;
     updates.AppendElement(aUpdate);
     CreateDecryptor(aOrigin, aTopLevelOrigin, aInPBMode, Move(updates));
   }
-  class Updates : public nsRunnable
+  class Updates : public Runnable
   {
   public:
     Updates(GMPStorageTest* aRunner, nsTArray<nsCString>&& aUpdates)
       : mRunner(aRunner),
         mUpdates(aUpdates)
     {
     }
 
--- a/dom/media/gtest/TestMP4Demuxer.cpp
+++ b/dom/media/gtest/TestMP4Demuxer.cpp
@@ -142,17 +142,17 @@ public:
   }
 
 private:
 
   template<typename FunctionType>
   void
   DispatchTask(FunctionType aFun)
   {
-    RefPtr<nsRunnable> r = NS_NewRunnableFunction(aFun);
+    RefPtr<Runnable> r = NS_NewRunnableFunction(aFun);
     mTaskQueue->Dispatch(r.forget());
   }
 
   virtual ~MP4DemuxerBinding()
   {
   }
 };
 
--- a/dom/media/gtest/TestMediaFormatReader.cpp
+++ b/dom/media/gtest/TestMediaFormatReader.cpp
@@ -123,17 +123,17 @@ public:
              [self]() {
                EXPECT_TRUE(false);
                self->mTaskQueue->BeginShutdown();
              }); //Then
   }
   template<class Function>
   void RunTestAndWait(Function&& aFunction)
   {
-    RefPtr<nsRunnable> r = NS_NewRunnableFunction(Forward<Function>(aFunction));
+    RefPtr<Runnable> r = NS_NewRunnableFunction(Forward<Function>(aFunction));
     mTaskQueue->Dispatch(r.forget());
     mTaskQueue->AwaitShutdownAndIdle();
   }
 private:
   ~MediaFormatReaderBinding()
   {}
 };
 
--- a/dom/media/gtest/TestMozPromise.cpp
+++ b/dom/media/gtest/TestMozPromise.cpp
@@ -29,17 +29,17 @@ public:
     mTaskQueue->AwaitShutdownAndIdle();
   }
 
   TaskQueue* Queue() { return mTaskQueue; }
 private:
   RefPtr<TaskQueue> mTaskQueue;
 };
 
-class DelayedResolveOrReject : public nsRunnable
+class DelayedResolveOrReject : public Runnable
 {
 public:
   DelayedResolveOrReject(TaskQueue* aTaskQueue,
                          TestPromise::Private* aPromise,
                          TestPromise::ResolveOrRejectValue aValue,
                          int aIterations)
   : mTaskQueue(aTaskQueue)
   , mPromise(aPromise)
--- a/dom/media/imagecapture/CaptureTask.cpp
+++ b/dom/media/imagecapture/CaptureTask.cpp
@@ -150,17 +150,17 @@ CaptureTask::NotifyEnded()
 }
 
 void
 CaptureTask::PostTrackEndEvent()
 {
   mImageGrabbedOrTrackEnd = true;
 
   // Got track end or finish event, stop the task.
-  class TrackEndRunnable : public nsRunnable
+  class TrackEndRunnable : public Runnable
   {
   public:
     explicit TrackEndRunnable(CaptureTask* aTask)
       : mTask(aTask) {}
 
     NS_IMETHOD Run()
     {
       mTask->TaskComplete(nullptr, NS_ERROR_FAILURE);
--- a/dom/media/mediasink/DecodedAudioDataSink.cpp
+++ b/dom/media/mediasink/DecodedAudioDataSink.cpp
@@ -24,46 +24,80 @@ extern LazyLogModule gMediaDecoderLog;
   MOZ_LOG(gMediaDecoderLog, LogLevel::Verbose, \
   ("DecodedAudioDataSink=%p " msg, this, ##__VA_ARGS__))
 
 namespace media {
 
 // The amount of audio frames that is used to fuzz rounding errors.
 static const int64_t AUDIO_FUZZ_FRAMES = 1;
 
-DecodedAudioDataSink::DecodedAudioDataSink(MediaQueue<MediaData>& aAudioQueue,
+// Amount of audio frames we will be processing ahead of use
+static const int32_t LOW_AUDIO_USECS = 300000;
+
+DecodedAudioDataSink::DecodedAudioDataSink(AbstractThread* aThread,
+                                           MediaQueue<MediaData>& aAudioQueue,
                                            int64_t aStartTime,
                                            const AudioInfo& aInfo,
                                            dom::AudioChannel aChannel)
   : AudioSink(aAudioQueue)
   , mStartTime(aStartTime)
-  , mWritten(0)
   , mLastGoodPosition(0)
   , mInfo(aInfo)
   , mChannel(aChannel)
   , mPlaying(true)
+  , mMonitor("DecodedAudioDataSink")
+  , mWritten(0)
+  , mErrored(false)
   , mPlaybackComplete(false)
+  , mOwnerThread(aThread)
+  , mProcessedQueueLength(0)
+  , mFramesParsed(0)
+  , mLastEndTime(0)
 {
   bool resampling = gfxPrefs::AudioSinkResampling();
-  uint32_t resamplingRate = gfxPrefs::AudioSinkResampleRate();
-  mConverter =
-    MakeUnique<AudioConverter>(
-      AudioConfig(mInfo.mChannels, mInfo.mRate),
-      AudioConfig(mInfo.mChannels > 2 && gfxPrefs::AudioSinkForceStereo()
-                    ? 2 : mInfo.mChannels,
-                  resampling ? resamplingRate : mInfo.mRate));
+
+  if (resampling) {
+    mOutputRate = gfxPrefs::AudioSinkResampleRate();
+  } else if (mInfo.mRate == 44100 || mInfo.mRate == 48000) {
+    // The original rate is of good quality and we want to minimize unecessary
+    // resampling. The common scenario being that the sampling rate is one or
+    // the other, this allows to minimize audio quality regression and hoping
+    // content provider want change from those rates mid-stream.
+    mOutputRate = mInfo.mRate;
+  } else {
+    // We will resample all data to match cubeb's preferred sampling rate.
+    mOutputRate = AudioStream::GetPreferredRate();
+  }
+  MOZ_DIAGNOSTIC_ASSERT(mOutputRate, "output rate can't be 0.");
+
+  bool monoAudioEnabled = gfxPrefs::MonoAudio();
+
+  mOutputChannels = monoAudioEnabled
+    ? 1 : (gfxPrefs::AudioSinkForceStereo() ? 2 : mInfo.mChannels);
 }
 
 DecodedAudioDataSink::~DecodedAudioDataSink()
 {
 }
 
 RefPtr<GenericPromise>
 DecodedAudioDataSink::Init(const PlaybackParams& aParams)
 {
+  MOZ_ASSERT(mOwnerThread->IsCurrentThreadIn());
+
+  mAudioQueueListener = mAudioQueue.PushEvent().Connect(
+    mOwnerThread, this, &DecodedAudioDataSink::OnAudioPushed);
+  mAudioQueueFinishListener = mAudioQueue.FinishEvent().Connect(
+    mOwnerThread, this, &DecodedAudioDataSink::NotifyAudioNeeded);
+  mProcessedQueueListener = mProcessedQueue.PopEvent().Connect(
+    mOwnerThread, this, &DecodedAudioDataSink::OnAudioPopped);
+
+  // To ensure at least one audio packet will be popped from AudioQueue and
+  // ready to be played.
+  NotifyAudioNeeded();
   RefPtr<GenericPromise> p = mEndPromise.Ensure(__func__);
   nsresult rv = InitializeAudioStream(aParams);
   if (NS_FAILED(rv)) {
     mEndPromise.Reject(rv, __func__);
   }
   return p;
 }
 
@@ -84,26 +118,40 @@ DecodedAudioDataSink::GetPosition()
   return mStartTime + mLastGoodPosition;
 }
 
 bool
 DecodedAudioDataSink::HasUnplayedFrames()
 {
   // Experimentation suggests that GetPositionInFrames() is zero-indexed,
   // so we need to add 1 here before comparing it to mWritten.
-  return mAudioStream && mAudioStream->GetPositionInFrames() + 1 < mWritten;
+  int64_t total;
+  {
+    MonitorAutoLock mon(mMonitor);
+    total = mWritten + (mCursor.get() ? mCursor->Available() : 0);
+  }
+  return mProcessedQueue.GetSize() ||
+         (mAudioStream && mAudioStream->GetPositionInFrames() + 1 < total);
 }
 
 void
 DecodedAudioDataSink::Shutdown()
 {
+  MOZ_ASSERT(mOwnerThread->IsCurrentThreadIn());
+
+  mAudioQueueListener.Disconnect();
+  mAudioQueueFinishListener.Disconnect();
+  mProcessedQueueListener.Disconnect();
+
   if (mAudioStream) {
     mAudioStream->Shutdown();
     mAudioStream = nullptr;
   }
+  mProcessedQueue.Reset();
+  mProcessedQueue.Finish();
   mEndPromise.ResolveIfExists(true, __func__);
 }
 
 void
 DecodedAudioDataSink::SetVolume(double aVolume)
 {
   if (mAudioStream) {
     mAudioStream->SetVolume(aVolume);
@@ -141,19 +189,17 @@ DecodedAudioDataSink::SetPlaying(bool aP
   }
   mPlaying = aPlaying;
 }
 
 nsresult
 DecodedAudioDataSink::InitializeAudioStream(const PlaybackParams& aParams)
 {
   mAudioStream = new AudioStream(*this);
-  nsresult rv = mAudioStream->Init(mConverter->OutputConfig().Channels(),
-                                   mConverter->OutputConfig().Rate(),
-                                   mChannel);
+  nsresult rv = mAudioStream->Init(mOutputChannels, mOutputRate, mChannel);
   if (NS_FAILED(rv)) {
     mAudioStream->Shutdown();
     mAudioStream = nullptr;
     return rv;
   }
 
   // Set playback params before calling Start() so they can take effect
   // as soon as the 1st DataCallback of the AudioStream fires.
@@ -163,23 +209,29 @@ DecodedAudioDataSink::InitializeAudioStr
   mAudioStream->Start();
 
   return NS_OK;
 }
 
 int64_t
 DecodedAudioDataSink::GetEndTime() const
 {
-  CheckedInt64 playedUsecs =
-    FramesToUsecs(mWritten, mConverter->OutputConfig().Rate()) + mStartTime;
+  int64_t written;
+  {
+    MonitorAutoLock mon(mMonitor);
+    written = mWritten;
+  }
+  CheckedInt64 playedUsecs = FramesToUsecs(written, mOutputRate) + mStartTime;
   if (!playedUsecs.isValid()) {
     NS_WARNING("Int overflow calculating audio end time");
     return -1;
   }
-  return playedUsecs.value();
+  // As we may be resampling, rounding errors may occur. Ensure we never get
+  // past the original end time.
+  return std::min<int64_t>(mLastEndTime, playedUsecs.value());
 }
 
 UniquePtr<AudioStream::Chunk>
 DecodedAudioDataSink::PopFrames(uint32_t aFrames)
 {
   class Chunk : public AudioStream::Chunk {
   public:
     Chunk(AudioData* aBuffer, uint32_t aFrames, AudioDataValue* aData)
@@ -212,123 +264,279 @@ DecodedAudioDataSink::PopFrames(uint32_t
     AudioDataValue* GetWritable() const { return mData.get(); }
   private:
     const uint32_t mFrames;
     const uint32_t mChannels;
     const uint32_t mRate;
     UniquePtr<AudioDataValue[]> mData;
   };
 
-  while (!mCurrentData) {
+  bool needPopping = false;
+  if (!mCurrentData) {
     // No data in the queue. Return an empty chunk.
-    if (AudioQueue().GetSize() == 0) {
+    if (!mProcessedQueue.GetSize()) {
       return MakeUnique<Chunk>();
     }
 
-    RefPtr<AudioData> a = AudioQueue().PeekFront()->As<AudioData>();
-
-    // Ignore the element with 0 frames and try next.
-    if (a->mFrames == 0) {
-      RefPtr<MediaData> releaseMe = AudioQueue().PopFront();
-      continue;
-    }
-
-    // Ignore invalid samples.
-    if (a->mRate != mInfo.mRate || a->mChannels != mInfo.mChannels) {
-      NS_WARNING(nsPrintfCString(
-        "mismatched sample format, data=%p rate=%u channels=%u frames=%u",
-        a->mAudioData.get(), a->mRate, a->mChannels, a->mFrames).get());
-      RefPtr<MediaData> releaseMe = AudioQueue().PopFront();
-      continue;
-    }
-
-    // See if there's a gap in the audio. If there is, push silence into the
-    // audio hardware, so we can play across the gap.
-    // Calculate the timestamp of the next chunk of audio in numbers of
-    // samples.
-    CheckedInt64 sampleTime = UsecsToFrames(AudioQueue().PeekFront()->mTime,
-                                            mConverter->OutputConfig().Rate());
-    // Calculate the number of frames that have been pushed onto the audio hardware.
-    CheckedInt64 playedFrames = UsecsToFrames(mStartTime,
-                                              mConverter->OutputConfig().Rate()) +
-                                static_cast<int64_t>(mWritten);
-    CheckedInt64 missingFrames = sampleTime - playedFrames;
-
-    if (!missingFrames.isValid() || !sampleTime.isValid()) {
-      NS_WARNING("Int overflow in DecodedAudioDataSink");
-      mErrored = true;
-      return MakeUnique<Chunk>();
+    // We need to update our values prior popping the processed queue in
+    // order to prevent the pop event to fire too early (prior
+    // mProcessedQueueLength being updated) or prevent HasUnplayedFrames
+    // to incorrectly return true during the time interval betweeen the
+    // when mProcessedQueue is read and mWritten is updated.
+    needPopping = true;
+    mCurrentData = mProcessedQueue.PeekFront();
+    {
+      MonitorAutoLock mon(mMonitor);
+      mCursor = MakeUnique<AudioBufferCursor>(mCurrentData->mAudioData.get(),
+                                              mCurrentData->mChannels,
+                                              mCurrentData->mFrames);
     }
-
-    const uint32_t rate = mConverter->OutputConfig().Rate();
-    const uint32_t channels = mConverter->OutputConfig().Channels();
-
-    if (missingFrames.value() > AUDIO_FUZZ_FRAMES) {
-      // The next audio chunk begins some time after the end of the last chunk
-      // we pushed to the audio hardware. We must push silence into the audio
-      // hardware so that the next audio chunk begins playback at the correct
-      // time.
-      missingFrames = std::min<int64_t>(UINT32_MAX, missingFrames.value());
-      auto framesToPop = std::min<uint32_t>(missingFrames.value(), aFrames);
-      mWritten += framesToPop;
-      return MakeUnique<SilentChunk>(framesToPop, channels, rate);
-    }
-
-    RefPtr<AudioData> data =
-      dont_AddRef(AudioQueue().PopFront().take()->As<AudioData>());
-    if (mConverter->InputConfig() != mConverter->OutputConfig()) {
-      AlignedAudioBuffer convertedData =
-        mConverter->Process(AudioSampleBuffer(Move(data->mAudioData))).Forget();
-      mCurrentData =
-        new AudioData(data->mOffset,
-                      data->mTime,
-                      data->mDuration,
-                      convertedData.Length() / channels,
-                      Move(convertedData),
-                      channels,
-                      rate);
-    } else {
-      mCurrentData = Move(data);
-    }
-
-    mCursor = MakeUnique<AudioBufferCursor>(mCurrentData->mAudioData.get(),
-                                            mCurrentData->mChannels,
-                                            mCurrentData->mFrames);
     MOZ_ASSERT(mCurrentData->mFrames > 0);
+    mProcessedQueueLength -=
+      FramesToUsecs(mCurrentData->mFrames, mOutputRate).value();
   }
 
   auto framesToPop = std::min(aFrames, mCursor->Available());
 
   SINK_LOG_V("playing audio at time=%lld offset=%u length=%u",
              mCurrentData->mTime, mCurrentData->mFrames - mCursor->Available(), framesToPop);
 
   UniquePtr<AudioStream::Chunk> chunk =
     MakeUnique<Chunk>(mCurrentData, framesToPop, mCursor->Ptr());
 
-  mWritten += framesToPop;
-  mCursor->Advance(framesToPop);
+  {
+    MonitorAutoLock mon(mMonitor);
+    mWritten += framesToPop;
+    mCursor->Advance(framesToPop);
+  }
 
   // All frames are popped. Reset mCurrentData so we can pop new elements from
   // the audio queue in next calls to PopFrames().
-  if (mCursor->Available() == 0) {
+  if (!mCursor->Available()) {
     mCurrentData = nullptr;
   }
 
+  if (needPopping) {
+    // We can now safely pop the audio packet from the processed queue.
+    // This will fire the popped event, triggering a call to NotifyAudioNeeded.
+    RefPtr<AudioData> releaseMe = mProcessedQueue.PopFront();
+  }
+
   return chunk;
 }
 
 bool
 DecodedAudioDataSink::Ended() const
 {
   // Return true when error encountered so AudioStream can start draining.
-  return AudioQueue().IsFinished() || mErrored;
+  return mProcessedQueue.IsFinished() || mErrored;
 }
 
 void
 DecodedAudioDataSink::Drained()
 {
   SINK_LOG("Drained");
   mPlaybackComplete = true;
   mEndPromise.ResolveIfExists(true, __func__);
 }
 
+void
+DecodedAudioDataSink::OnAudioPopped(const RefPtr<MediaData>& aSample)
+{
+  SINK_LOG_V("AudioStream has used an audio packet.");
+  NotifyAudioNeeded();
+}
+
+void
+DecodedAudioDataSink::OnAudioPushed(const RefPtr<MediaData>& aSample)
+{
+  SINK_LOG_V("One new audio packet available.");
+  NotifyAudioNeeded();
+}
+
+void
+DecodedAudioDataSink::NotifyAudioNeeded()
+{
+  MOZ_ASSERT(mOwnerThread->IsCurrentThreadIn(),
+             "Not called from the owner's thread");
+
+  // Always ensure we have two processed frames pending to allow for processing
+  // latency.
+  while (AudioQueue().GetSize() && (AudioQueue().IsFinished() ||
+                                    mProcessedQueueLength < LOW_AUDIO_USECS ||
+                                    mProcessedQueue.GetSize() < 2)) {
+    RefPtr<AudioData> data =
+      dont_AddRef(AudioQueue().PopFront().take()->As<AudioData>());
+
+    // Ignore the element with 0 frames and try next.
+    if (!data->mFrames) {
+      continue;
+    }
+
+    if (!mConverter ||
+        (data->mRate != mConverter->InputConfig().Rate() ||
+         data->mChannels != mConverter->InputConfig().Channels())) {
+      SINK_LOG_V("Audio format changed from %u@%uHz to %u@%uHz",
+                 mConverter? mConverter->InputConfig().Channels() : 0,
+                 mConverter ? mConverter->InputConfig().Rate() : 0,
+                 data->mChannels, data->mRate);
+
+      DrainConverter();
+
+      // mFramesParsed indicates the current playtime in frames at the current
+      // input sampling rate. Recalculate it per the new sampling rate.
+      if (mFramesParsed) {
+        // We minimize overflow.
+        uint32_t oldRate = mConverter->InputConfig().Rate();
+        uint32_t newRate = data->mRate;
+        CheckedInt64 result = SaferMultDiv(mFramesParsed, newRate, oldRate);
+        if (!result.isValid()) {
+          NS_WARNING("Int overflow in DecodedAudioDataSink");
+          mErrored = true;
+          return;
+        }
+        mFramesParsed = result.value();
+      }
+
+      mConverter =
+        MakeUnique<AudioConverter>(
+          AudioConfig(data->mChannels, data->mRate),
+          AudioConfig(mOutputChannels, mOutputRate));
+    }
+
+    // See if there's a gap in the audio. If there is, push silence into the
+    // audio hardware, so we can play across the gap.
+    // Calculate the timestamp of the next chunk of audio in numbers of
+    // samples.
+    CheckedInt64 sampleTime = UsecsToFrames(data->mTime - mStartTime,
+                                            data->mRate);
+    // Calculate the number of frames that have been pushed onto the audio hardware.
+    CheckedInt64 missingFrames = sampleTime - mFramesParsed;
+
+    if (!missingFrames.isValid()) {
+      NS_WARNING("Int overflow in DecodedAudioDataSink");
+      mErrored = true;
+      return;
+    }
+
+    if (missingFrames.value() > AUDIO_FUZZ_FRAMES) {
+      // The next audio packet begins some time after the end of the last packet
+      // we pushed to the audio hardware. We must push silence into the audio
+      // hardware so that the next audio packet begins playback at the correct
+      // time.
+      missingFrames = std::min<int64_t>(INT32_MAX, missingFrames.value());
+      mFramesParsed += missingFrames.value();
+
+      // We need to calculate how many frames are missing at the output rate.
+      missingFrames =
+        SaferMultDiv(missingFrames.value(), mOutputRate, data->mRate);
+      if (!missingFrames.isValid()) {
+        NS_WARNING("Int overflow in DecodedAudioDataSink");
+        mErrored = true;
+        return;
+      }
+
+      // We need to insert silence, first use drained frames if any.
+      missingFrames -= DrainConverter(missingFrames.value());
+      // Insert silence if still needed.
+      if (missingFrames.value()) {
+        AlignedAudioBuffer silenceData(missingFrames.value() * mOutputChannels);
+        if (!silenceData) {
+          NS_WARNING("OOM in DecodedAudioDataSink");
+          mErrored = true;
+          return;
+        }
+        RefPtr<AudioData> silence = CreateAudioFromBuffer(Move(silenceData), data);
+        PushProcessedAudio(silence);
+      }
+    }
+
+    mLastEndTime = data->GetEndTime();
+    mFramesParsed += data->mFrames;
+
+    if (mConverter->InputConfig() != mConverter->OutputConfig()) {
+      AlignedAudioBuffer convertedData =
+        mConverter->Process(AudioSampleBuffer(Move(data->mAudioData))).Forget();
+      data = CreateAudioFromBuffer(Move(convertedData), data);
+    }
+    if (PushProcessedAudio(data)) {
+      mLastProcessedPacket = Some(data);
+    }
+  }
+
+  if (AudioQueue().IsFinished()) {
+    // We have reached the end of the data, drain the resampler.
+    DrainConverter();
+    mProcessedQueue.Finish();
+  }
+}
+
+uint32_t
+DecodedAudioDataSink::PushProcessedAudio(AudioData* aData)
+{
+  if (!aData || !aData->mFrames) {
+    return 0;
+  }
+  mProcessedQueue.Push(aData);
+  mProcessedQueueLength += FramesToUsecs(aData->mFrames, mOutputRate).value();
+  return aData->mFrames;
+}
+
+already_AddRefed<AudioData>
+DecodedAudioDataSink::CreateAudioFromBuffer(AlignedAudioBuffer&& aBuffer,
+                                            AudioData* aReference)
+{
+  uint32_t frames = aBuffer.Length() / mOutputChannels;
+  if (!frames) {
+    return nullptr;
+  }
+  CheckedInt64 duration = FramesToUsecs(frames, mOutputRate);
+  if (!duration.isValid()) {
+    NS_WARNING("Int overflow in DecodedAudioDataSink");
+    mErrored = true;
+    return nullptr;
+  }
+  RefPtr<AudioData> data =
+    new AudioData(aReference->mOffset,
+                  aReference->mTime,
+                  duration.value(),
+                  frames,
+                  Move(aBuffer),
+                  mOutputChannels,
+                  mOutputRate);
+  return data.forget();
+}
+
+uint32_t
+DecodedAudioDataSink::DrainConverter(uint32_t aMaxFrames)
+{
+  MOZ_ASSERT(mOwnerThread->IsCurrentThreadIn());
+
+  if (!mConverter || !mLastProcessedPacket || !aMaxFrames) {
+    // nothing to drain.
+    return 0;
+  }
+
+  RefPtr<AudioData> lastPacket = mLastProcessedPacket.ref();
+  mLastProcessedPacket.reset();
+
+  // To drain we simply provide an empty packet to the audio converter.
+  AlignedAudioBuffer convertedData =
+    mConverter->Process(AudioSampleBuffer(AlignedAudioBuffer())).Forget();
+
+  uint32_t frames = convertedData.Length() / mOutputChannels;
+  if (!convertedData.SetLength(std::min(frames, aMaxFrames) * mOutputChannels)) {
+    // This can never happen as we were reducing the length of convertData.
+    mErrored = true;
+    return 0;
+  }
+
+  RefPtr<AudioData> data =
+    CreateAudioFromBuffer(Move(convertedData), lastPacket);
+  if (!data) {
+    return 0;
+  }
+  mProcessedQueue.Push(data);
+  return data->mFrames;
+}
+
 } // namespace media
 } // namespace mozilla
--- a/dom/media/mediasink/DecodedAudioDataSink.h
+++ b/dom/media/mediasink/DecodedAudioDataSink.h
@@ -12,28 +12,29 @@
 #include "MediaInfo.h"
 #include "mozilla/RefPtr.h"
 #include "nsISupportsImpl.h"
 
 #include "mozilla/dom/AudioChannelBinding.h"
 #include "mozilla/Atomics.h"
 #include "mozilla/Maybe.h"
 #include "mozilla/MozPromise.h"
-#include "mozilla/ReentrantMonitor.h"
+#include "mozilla/Monitor.h"
 
 namespace mozilla {
 
 class AudioConverter;
 
 namespace media {
 
 class DecodedAudioDataSink : public AudioSink,
                              private AudioStream::DataSource {
 public:
-  DecodedAudioDataSink(MediaQueue<MediaData>& aAudioQueue,
+  DecodedAudioDataSink(AbstractThread* aThread,
+                       MediaQueue<MediaData>& aAudioQueue,
                        int64_t aStartTime,
                        const AudioInfo& aInfo,
                        dom::AudioChannel aChannel);
 
   // Return a promise which will be resolved when DecodedAudioDataSink
   // finishes playing, or rejected if any error.
   RefPtr<GenericPromise> Init(const PlaybackParams& aParams) override;
 
@@ -71,19 +72,16 @@ private:
   // The audio stream resource. Used on the task queue of MDSM only.
   RefPtr<AudioStream> mAudioStream;
 
   // The presentation time of the first audio frame that was played in
   // microseconds. We can add this to the audio stream position to determine
   // the current audio time.
   const int64_t mStartTime;
 
-  // PCM frames written to the stream so far.
-  Atomic<int64_t> mWritten;
-
   // Keep the last good position returned from the audio stream. Used to ensure
   // position returned by GetPosition() is mono-increasing in spite of audio
   // stream error. Used on the task queue of MDSM only.
   int64_t mLastGoodPosition;
 
   const AudioInfo mInfo;
 
   const dom::AudioChannel mChannel;
@@ -94,23 +92,62 @@ private:
   MozPromiseHolder<GenericPromise> mEndPromise;
 
   /*
    * Members to implement AudioStream::DataSource.
    * Used on the callback thread of cubeb.
    */
   // The AudioData at which AudioStream::DataSource is reading.
   RefPtr<AudioData> mCurrentData;
+
+  // Monitor protecting access to mCursor and mWritten.
+  // mCursor is created/destroyed on the cubeb thread, while we must also
+  // ensure that mWritten and mCursor::Available() get modified simultaneously.
+  // (written on cubeb thread, and read on MDSM task queue).
+  mutable Monitor mMonitor;
   // Keep track of the read position of mCurrentData.
   UniquePtr<AudioBufferCursor> mCursor;
+
+  // PCM frames written to the stream so far.
+  int64_t mWritten;
+
   // True if there is any error in processing audio data like overflow.
-  bool mErrored = false;
+  Atomic<bool> mErrored;
 
   // Set on the callback thread of cubeb once the stream has drained.
   Atomic<bool> mPlaybackComplete;
 
+  const RefPtr<AbstractThread> mOwnerThread;
+
+  // Audio Processing objects and methods
+  void OnAudioPopped(const RefPtr<MediaData>& aSample);
+  void OnAudioPushed(const RefPtr<MediaData>& aSample);
+  void NotifyAudioNeeded();
+  // Drain the converter and add the output to the processed audio queue.
+  // A maximum of aMaxFrames will be added.
+  uint32_t DrainConverter(uint32_t aMaxFrames = UINT32_MAX);
+  already_AddRefed<AudioData> CreateAudioFromBuffer(AlignedAudioBuffer&& aBuffer,
+                                                    AudioData* aReference);
+  // Add data to the processsed queue, update mProcessedQueueLength and
+  // return the number of frames added.
+  uint32_t PushProcessedAudio(AudioData* aData);
   UniquePtr<AudioConverter> mConverter;
+  MediaQueue<AudioData> mProcessedQueue;
+  // Length in microseconds of the ProcessedQueue
+  Atomic<int32_t> mProcessedQueueLength;
+  MediaEventListener mAudioQueueListener;
+  MediaEventListener mAudioQueueFinishListener;
+  MediaEventListener mProcessedQueueListener;
+  // Number of frames processed from AudioQueue(). Used to determine gaps in
+  // the input stream. It indicates the time in frames since playback started
+  // at the current input framerate.
+  int64_t mFramesParsed;
+  Maybe<RefPtr<AudioData>> mLastProcessedPacket;
+  int64_t mLastEndTime;
+  // Never modifed after construction.
+  uint32_t mOutputRate;
+  uint32_t mOutputChannels;
 };
 
 } // namespace media
 } // namespace mozilla
 
 #endif
--- a/dom/media/mediasink/DecodedStream.cpp
+++ b/dom/media/mediasink/DecodedStream.cpp
@@ -265,17 +265,17 @@ DecodedStream::Start(int64_t aStartTime,
   AssertOwnerThread();
   MOZ_ASSERT(mStartTime.isNothing(), "playback already started.");
 
   mStartTime.emplace(aStartTime);
   mInfo = aInfo;
   mPlaying = true;
   ConnectListener();
 
-  class R : public nsRunnable {
+  class R : public Runnable {
     typedef MozPromiseHolder<GenericPromise> Promise;
   public:
     R(PlaybackInfoInit&& aInit, Promise&& aPromise, OutputStreamManager* aManager)
       : mInit(Move(aInit)), mOutputStreamManager(aManager)
     {
       mPromise = Move(aPromise);
     }
     NS_IMETHOD Run() override
--- a/dom/media/mediasource/AsyncEventRunner.h
+++ b/dom/media/mediasource/AsyncEventRunner.h
@@ -7,17 +7,17 @@
 #ifndef MOZILLA_ASYNCEVENTRUNNER_H_
 #define MOZILLA_ASYNCEVENTRUNNER_H_
 
 #include "nsThreadUtils.h"
 
 namespace mozilla {
 
 template <typename T>
-class AsyncEventRunner : public nsRunnable
+class AsyncEventRunner : public Runnable
 {
 public:
   AsyncEventRunner(T* aTarget, const char* aName)
     : mTarget(aTarget)
     , mName(aName)
   {}
 
   NS_IMETHOD Run() override
--- a/dom/media/mediasource/TrackBuffersManager.cpp
+++ b/dom/media/mediasource/TrackBuffersManager.cpp
@@ -54,17 +54,17 @@ AppendStateToStr(SourceBufferAttributes:
     default:
       return "IMPOSSIBLE";
   }
 }
 
 static Atomic<uint32_t> sStreamSourceID(0u);
 
 #ifdef MOZ_EME
-class DispatchKeyNeededEvent : public nsRunnable {
+class DispatchKeyNeededEvent : public Runnable {
 public:
   DispatchKeyNeededEvent(AbstractMediaDecoder* aDecoder,
                          nsTArray<uint8_t>& aInitData,
                          const nsString& aInitDataType)
     : mDecoder(aDecoder)
     , mInitData(aInitData)
     , mInitDataType(aInitDataType)
   {
@@ -1089,24 +1089,16 @@ TrackBuffersManager::OnDemuxerInitDone(n
     // This is handled by SourceBuffer once the promise is resolved.
     if (activeTrack) {
       mActiveTrack = true;
     }
 
     // 6. Set first initialization segment received flag to true.
     mFirstInitializationSegmentReceived = true;
   } else {
-    // Check that audio configuration hasn't changed as this is something
-    // we do not support yet (bug 1185827).
-    if (mAudioTracks.mNumTracks &&
-        (info.mAudio.mChannels != mAudioTracks.mInfo->GetAsAudioInfo()->mChannels ||
-         info.mAudio.mRate != mAudioTracks.mInfo->GetAsAudioInfo()->mRate)) {
-      RejectAppend(NS_ERROR_FAILURE, __func__);
-      return;
-    }
     mAudioTracks.mLastInfo = new SharedTrackInfo(info.mAudio, streamID);
     mVideoTracks.mLastInfo = new SharedTrackInfo(info.mVideo, streamID);
   }
 
   UniquePtr<EncryptionInfo> crypto = mInputDemuxer->GetCrypto();
   if (crypto && crypto->IsEncrypted()) {
 #ifdef MOZ_EME
     // Try and dispatch 'encrypted'. Won't go if ready state still HAVE_NOTHING.
new file mode 100644
index 0000000000000000000000000000000000000000..56506e1f2da0b9304bafc93d3b26e2d88d1f1339
GIT binary patch
literal 24328
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
new file mode 100644
--- /dev/null
+++ b/dom/media/mediasource/test/aac20-48000-64000-1.m4s^headers^
@@ -0,0 +1,1 @@
+Cache-Control: no-store
new file mode 100644
index 0000000000000000000000000000000000000000..3faff17ebf709d76b471751ba9e3f0e37e522b00
GIT binary patch
literal 24132
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
new file mode 100644
--- /dev/null
+++ b/dom/media/mediasource/test/aac20-48000-64000-2.m4s^headers^
@@ -0,0 +1,1 @@
+Cache-Control: no-store
new file mode 100644
index 0000000000000000000000000000000000000000..b70e01651272eeebaf6f192f833e45aadbd451ec
GIT binary patch
literal 1246
zc$}4y&npCB7{{L(cFjRq;kJi4NK49rxG0i?3m2ti7h~Vqb~Epe=AGSep_JS>ILHw>
z@J}cQ2M44a<jToGxhe6!W7d4Pm3Z3seLv6hexD!jED<Gh{>qZDi)E6g&Vq3JnI-Z>
z`V@Cv6?b?!&(!^umzq|KD08NK(t=-PRZguxOuw2g6OMh)T9lmj7lWP+QO}y{QHy`|
z)kZigSQ1RmetuWmMIh|UGsmlB3Aa?lDwEP@=D00OnPXOwId&j@;)P;Po(aLfYKPX&
zzT!#d**Tc9vE(^s$S1;IaO62Fe8E67!I%21nwRO6P)GPrblHLl1$9Ze)wd3}QCz}X
zuwt>6#MI+nT+@Ted|$w1(id6qTcy8R{r!|C>w-VX%l5L;ay!qyN4h^!yXkwuU1eIi
z>ai9R1-7hx--q*8TWp<lgSzKwM>>CF?S(qq1D2o0_`Qc=$Sp-QXONZ*b7n^)&OAVT
z6L=Tc2JVI2OW;$`90K0}6X*{jo^v5S0QxLw_9IR|fo20Z4s}i-cL+3hP^Sqr9gy1t
l`fK1@;Pao~n|_9x%}{d<^dAu42HpZq8Tb`6Gf@A%!k<Iwpxyug
new file mode 100644
--- /dev/null
+++ b/dom/media/mediasource/test/aac20-48000-64000-init.mp4^headers^
@@ -0,0 +1,1 @@
+Cache-Control: no-store
new file mode 100644
index 0000000000000000000000000000000000000000..3424acfecca8ef311a09914026d0b81f2b002977
GIT binary patch
literal 48979
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%0ABxfdjtX0djz)?Swl^I$RJ>*Qmg
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
UWUK!Bl9le(my$r1{~eqDKXY#LCIA2c
new file mode 100644
--- /dev/null
+++ b/dom/media/mediasource/test/aac51-48000-128000-1.m4s^headers^
@@ -0,0 +1,1 @@
+Cache-Control: no-store
new file mode 100644
index 0000000000000000000000000000000000000000..b02bfd043d38d87da6538f3fd72813aee7d2b675
GIT binary patch
literal 47727
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
new file mode 100644
--- /dev/null
+++ b/dom/media/mediasource/test/aac51-48000-128000-2.m4s^headers^
@@ -0,0 +1,1 @@
+Cache-Control: no-store
new file mode 100644
index 0000000000000000000000000000000000000000..7d62401f288eb36868b7eba94a8013cb73516141
GIT binary patch
literal 634
zc${NkV30{GsVpc?%`0O70uY^9oNtzrSe(JYz!aC8pAQnx$t}xB0m+{)(uf3M28P%J
zAU*>l7$E=(2b1r>fEO?UHLNQsO3VhbV@k5YcCsVv#4sIU1xfZYdgZ2MCIT4>xhdHF
zC3+mJ&?F-zrwFF2IKMOx*_2=)KSjYe6=;-#M`B(|PAXXGyWGsYG$1WdoC`4<3RF@c
z;xZ{kscA^A<S8x6QGl{H6_+IC0O_>ilHwF3HDS30CW#n6V`C5iQP7w$N-a()1~Hgb
zfCP(-gD8U#Q1uruX5|%TVC`UK@K6+B2zxq%jgblL!jh6=Bo_kt#mPu~5g@+`H5@@|
llJk-HHo0Y~6(F^_sTnD7r`=itA{9!Cz;ZBG12GF+BLJ)tR8s%|
new file mode 100644
--- /dev/null
+++ b/dom/media/mediasource/test/aac51-48000-128000-init.mp4^headers^
@@ -0,0 +1,1 @@
+Cache-Control: no-store
--- a/dom/media/mediasource/test/mochitest.ini
+++ b/dom/media/mediasource/test/mochitest.ini
@@ -29,24 +29,32 @@ support-files =
   bipbop/bipbop6.m4s^headers^ bipbop/bipbop_audio6.m4s^headers^ bipbop/bipbop_video6.m4s^headers^
   bipbop/bipbop7.m4s^headers^ bipbop/bipbop_audio7.m4s^headers^ bipbop/bipbop_video7.m4s^headers^
   bipbop/bipbop8.m4s^headers^ bipbop/bipbop_audio8.m4s^headers^ bipbop/bipbop_video8.m4s^headers^
   bipbop/bipbop9.m4s^headers^ bipbop/bipbop_audio9.m4s^headers^ bipbop/bipbop_video9.m4s^headers^
   bipbop/bipbop10.m4s^headers^ bipbop/bipbop_audio10.m4s^headers^ bipbop/bipbop_video10.m4s^headers^
   bipbop/bipbop11.m4s^headers^ bipbop/bipbop_audio11.m4s^headers^ bipbop/bipbop_video11.m4s^headers^
   bipbop/bipbop12.m4s^headers^ bipbop/bipbop_video12.m4s^headers^
   bipbop/bipbop13.m4s^headers^ bipbop/bipbop_video13.m4s^headers^
+  aac20-48000-64000-init.mp4   aac20-48000-64000-init.mp4^headers^
+  aac20-48000-64000-1.m4s aac20-48000-64000-1.m4s^headers^
+  aac20-48000-64000-2.m4s aac20-48000-64000-2.m4s^headers^
+  aac51-48000-128000-init.mp4 aac51-48000-128000-init.mp4^headers^
+  aac51-48000-128000-1.m4s aac51-48000-128000-1.m4s^headers^
+  aac51-48000-128000-2.m4s aac51-48000-128000-2.m4s^headers^
 
+[test_AudioChange_mp4.html]
+skip-if = ((os == "win" && os_version == "5.1") || (toolkit == 'android')) # Not supported on xp and android 2.3
 [test_BufferedSeek.html]
 [test_BufferedSeek_mp4.html]
 skip-if = ((os == "win" && os_version == "5.1") || (toolkit == 'android')) # Not supported on xp and android 2.3
 [test_BufferingWait.html]
 skip-if = toolkit == 'android' #timeout android bug 1199531
-#[test_BufferingWait_mp4.html] #intermittent timeout bug 1258922
-#skip-if = ((os == "win" && os_version == "5.1") || (toolkit == 'android')) # Not supported on xp and android 2.3
+[test_BufferingWait_mp4.html]
+skip-if = ((os == "win" && os_version == "5.1") || (toolkit == 'android')) # Not supported on xp and android 2.3
 [test_DrainOnMissingData_mp4.html]
 skip-if = ((os == "win" && os_version == "5.1") || (toolkit == 'android')) # Not supported on xp and android 2.3
 [test_EndOfStream.html]
 skip-if = (true || toolkit == 'android' || buildapp == 'mulet') #timeout android/mulet only bug 1101187 and bug 1182946
 [test_EndOfStream_mp4.html]
 skip-if = ((os == "win" && os_version == "5.1") || (toolkit == 'android' || buildapp == 'mulet')) # Not supported on xp and android 2.3
 [test_DurationUpdated.html]
 [test_DurationUpdated_mp4.html]
new file mode 100644
--- /dev/null
+++ b/dom/media/mediasource/test/test_AudioChange_mp4.html
@@ -0,0 +1,72 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+  <title>MSE: basic functionality</title>
+  <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <script type="text/javascript" src="mediasource.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+
+SimpleTest.waitForExplicitFinish();
+
+// This test checks loading a stereo segment, followed by a 5.1 segment plays without error.
+
+runWithMSE(function(ms, el) {
+  el.controls = true;
+  once(ms, 'sourceopen').then(function() {
+    // Log events for debugging.
+    var events = ["suspend", "play", "canplay", "canplaythrough", "loadstart", "loadedmetadata",
+                  "loadeddata", "playing", "ended", "error", "stalled", "emptied", "abort",
+                  "waiting", "pause", "durationchange", "seeking", "seeked"];
+    function logEvent(e) {
+      var v = e.target;
+      info("got " + e.type + " event");
+    }
+    events.forEach(function(e) {
+      el.addEventListener(e, logEvent, false);
+    });
+
+    ok(true, "Receive a sourceopen event");
+    var audiosb = ms.addSourceBuffer("audio/mp4");
+    el.addEventListener("error", function(e) {
+      ok(false, "should not fire '" + e.type + "' event");
+      SimpleTest.finish();
+    });
+    is(el.readyState, el.HAVE_NOTHING, "readyState is HAVE_NOTHING");
+    fetchAndLoad(audiosb, 'aac20-48000-64000-', ['init'], '.mp4')
+    .then(once.bind(null, el, 'loadedmetadata'))
+    .then(function() {
+      ok(true, "got loadedmetadata event");
+      var promises = [];
+      promises.push(once(el, 'loadeddata'));
+      promises.push(once(el, 'canplay'));
+      promises.push(fetchAndLoad(audiosb, 'aac20-48000-64000-', ['1'], '.m4s'));
+      return Promise.all(promises);
+    })
+    .then(function() {
+      ok(true, "got canplay event");
+      el.play();
+      return fetchAndLoad(audiosb, 'aac51-48000-128000-', ['init'], '.mp4');
+    })
+    .then(fetchAndLoad.bind(null, audiosb, 'aac51-48000-128000-', ['2'], '.m4s'))
+    .then(function() {
+      var promises = [];
+      ms.endOfStream();
+      promises.push(once(el, 'ended'));
+      promises.push(once(audiosb, 'updateend'));
+      return Promise.all(promises);
+    })
+    .then(function() {
+      ok(el.currentTime >= 6, "played to the end");
+      SimpleTest.finish();
+    })
+  });
+});
+
+</script>
+</pre>
+</body>
+</html>
--- a/dom/media/omx/MediaOmxReader.cpp
+++ b/dom/media/omx/MediaOmxReader.cpp
@@ -61,17 +61,17 @@ private:
 // thread, an instance of this class is scheduled to the main thread for
 // parsing the MP3 stream. The decode thread waits until it has finished.
 //
 // If there is more data available from the file, the runnable dispatches
 // a task to the IO thread for retrieving the next chunk of data, and
 // the IO task dispatches a runnable to the main thread for parsing the
 // data. This goes on until all of the MP3 file has been parsed.
 
-class MediaOmxReader::NotifyDataArrivedRunnable : public nsRunnable
+class MediaOmxReader::NotifyDataArrivedRunnable : public Runnable
 {
 public:
   NotifyDataArrivedRunnable(MediaOmxReader* aOmxReader,
                             uint64_t aLength,
                             int64_t aOffset, uint64_t aFullLength)
   : mOmxReader(aOmxReader),
     mLength(aLength),
     mOffset(aOffset),
--- a/dom/media/platforms/agnostic/BlankDecoderModule.cpp
+++ b/dom/media/platforms/agnostic/BlankDecoderModule.cpp
@@ -38,17 +38,17 @@ public:
   RefPtr<InitPromise> Init() override {
     return InitPromise::CreateAndResolve(mType, __func__);
   }
 
   nsresult Shutdown() override {
     return NS_OK;
   }
 
-  class OutputEvent : public nsRunnable {
+  class OutputEvent : public Runnable {
   public:
     OutputEvent(MediaRawData* aSample,
                 MediaDataDecoderCallback* aCallback,
                 BlankMediaDataCreator* aCreator)
       : mSample(aSample)
       , mCreator(aCreator)
       , mCallback(aCallback)
     {
--- a/dom/media/platforms/agnostic/gmp/MediaDataDecoderProxy.h
+++ b/dom/media/platforms/agnostic/gmp/MediaDataDecoderProxy.h
@@ -10,17 +10,17 @@
 #include "PlatformDecoderModule.h"
 #include "mozilla/RefPtr.h"
 #include "nsThreadUtils.h"
 #include "nscore.h"
 #include "GMPService.h"
 
 namespace mozilla {
 
-class InputTask : public nsRunnable {
+class InputTask : public Runnable {
 public:
   InputTask(MediaDataDecoder* aDecoder,
             MediaRawData* aSample)
    : mDecoder(aDecoder)
    , mSample(aSample)
   {}
 
   NS_IMETHOD Run() {
--- a/dom/media/platforms/wmf/WMFVideoMFTManager.cpp
+++ b/dom/media/platforms/wmf/WMFVideoMFTManager.cpp
@@ -144,17 +144,17 @@ WMFVideoMFTManager::GetMediaSubtypeGUID(
   switch (mStreamType) {
     case H264: return MFVideoFormat_H264;
     case VP8: return MFVideoFormat_VP80;
     case VP9: return MFVideoFormat_VP90;
     default: return GUID_NULL;
   };
 }
 
-class CreateDXVAManagerEvent : public nsRunnable {
+class CreateDXVAManagerEvent : public Runnable {
 public:
   CreateDXVAManagerEvent(LayersBackend aBackend, nsCString& aFailureReason)
     : mBackend(aBackend)
     , mFailureReason(aFailureReason)
   {}
 
   NS_IMETHOD Run() {
     NS_ASSERTION(NS_IsMainThread(), "Must be on main thread.");
--- a/dom/media/systemservices/CamerasChild.cpp
+++ b/dom/media/systemservices/CamerasChild.cpp
@@ -35,17 +35,17 @@ CamerasSingleton::CamerasSingleton()
     mCamerasChildThread(nullptr) {
   LOG(("CamerasSingleton: %p", this));
 }
 
 CamerasSingleton::~CamerasSingleton() {
   LOG(("~CamerasSingleton: %p", this));
 }
 
-class InitializeIPCThread : public nsRunnable
+class InitializeIPCThread : public Runnable
 {
 public:
   InitializeIPCThread()
     : mCamerasChild(nullptr) {}
 
   NS_IMETHOD Run() override {
     // Try to get the PBackground handle
     ipc::PBackgroundChild* existingBackgroundChild =
@@ -479,34 +479,34 @@ Shutdown(void)
     // We don't want to cause everything to get fired up if we're
     // really already shut down.
     LOG(("Shutdown when already shut down"));
     return;
   }
   child->ShutdownAll();
 }
 
-class ShutdownRunnable : public nsRunnable {
+class ShutdownRunnable : public Runnable {
 public:
-  ShutdownRunnable(RefPtr<nsRunnable> aReplyEvent,
+  ShutdownRunnable(RefPtr<Runnable> aReplyEvent,
                    nsIThread* aReplyThread)
     : mReplyEvent(aReplyEvent), mReplyThread(aReplyThread) {};
 
   NS_IMETHOD Run() override {
     LOG(("Closing BackgroundChild"));
     ipc::BackgroundChild::CloseForCurrentThread();
 
     LOG(("PBackground thread exists, shutting down thread"));
     mReplyThread->Dispatch(mReplyEvent, NS_DISPATCH_NORMAL);
 
     return NS_OK;
   }
 
 private:
-  RefPtr<nsRunnable> mReplyEvent;
+  RefPtr<Runnable> mReplyEvent;
   nsIThread* mReplyThread;
 };
 
 void
 CamerasChild::ShutdownAll()
 {
   // Called with CamerasSingleton::Mutex() held
   ShutdownParent();
@@ -520,17 +520,17 @@ CamerasChild::ShutdownParent()
   {
     MonitorAutoLock monitor(mReplyMonitor);
     mIPCIsAlive = false;
     monitor.NotifyAll();
   }
   if (CamerasSingleton::Thread()) {
     LOG(("Dispatching actor deletion"));
     // Delete the parent actor.
-    RefPtr<nsRunnable> deleteRunnable =
+    RefPtr<Runnable> deleteRunnable =
       // CamerasChild (this) will remain alive and is only deleted by the
       // IPC layer when SendAllDone returns.
       media::NewRunnableFrom([this]() -> nsresult {
         Unused << this->SendAllDone();
         return NS_OK;
       });
     CamerasSingleton::Thread()->Dispatch(deleteRunnable, NS_DISPATCH_NORMAL);
   } else {
@@ -541,17 +541,17 @@ CamerasChild::ShutdownParent()
 void
 CamerasChild::ShutdownChild()
 {
   // Called with CamerasSingleton::Mutex() held
   if (CamerasSingleton::Thread()) {
     LOG(("PBackground thread exists, dispatching close"));
     // Dispatch closing the IPC thread back to us when the
     // BackgroundChild is closed.
-    RefPtr<nsRunnable> event =
+    RefPtr<Runnable> event =
       new ThreadDestructor(CamerasSingleton::Thread());
     RefPtr<ShutdownRunnable> runnable =
       new ShutdownRunnable(event, NS_GetCurrentThread());
     CamerasSingleton::Thread()->Dispatch(runnable, NS_DISPATCH_NORMAL);
   } else {
     LOG(("Shutdown called without PBackground thread"));
   }
   LOG(("Erasing sCameras & thread refs (original thread)"));
--- a/dom/media/systemservices/CamerasParent.cpp
+++ b/dom/media/systemservices/CamerasParent.cpp
@@ -35,17 +35,17 @@ namespace camera {
 // - the main thread for some setups, and occassionally for video capture setup
 //   calls that don't work correctly elsewhere.
 // - the IPC thread on which PBackground is running and which receives and
 //   sends messages
 // - a thread which will execute the actual (possibly slow) camera access
 //   called "VideoCapture". On Windows this is a thread with an event loop
 //   suitable for UI access.
 
-class FrameSizeChangeRunnable : public nsRunnable {
+class FrameSizeChangeRunnable : public Runnable {
 public:
   FrameSizeChangeRunnable(CamerasParent *aParent, CaptureEngine capEngine,
                           int cap_id, unsigned int aWidth, unsigned int aHeight)
     : mParent(aParent), mCapEngine(capEngine), mCapId(cap_id),
       mWidth(aWidth), mHeight(aHeight) {}
 
   NS_IMETHOD Run() {
     if (mParent->IsShuttingDown()) {
@@ -84,17 +84,17 @@ CallbackHelper::FrameSizeChange(unsigned
     new FrameSizeChangeRunnable(mParent, mCapEngine, mCapturerId, w, h);
   MOZ_ASSERT(mParent);
   nsIThread * thread = mParent->GetBackgroundThread();
   MOZ_ASSERT(thread != nullptr);
   thread->Dispatch(runnable, NS_DISPATCH_NORMAL);
   return 0;
 }
 
-class DeliverFrameRunnable : public nsRunnable {
+class DeliverFrameRunnable : public Runnable {
 public:
   DeliverFrameRunnable(CamerasParent *aParent,
                        CaptureEngine engine,
                        int cap_id,
                        ShmemBuffer buffer,
                        unsigned char* altbuffer,
                        size_t size,
                        uint32_t time_stamp,
@@ -160,17 +160,17 @@ CamerasParent::Observe(nsISupports *aSub
   nsCOMPtr<nsIObserverService> obs = services::GetObserverService();
   MOZ_ASSERT(obs);
   obs->RemoveObserver(this, NS_XPCOM_WILL_SHUTDOWN_OBSERVER_ID);
   StopVideoCapture();
   return NS_OK;
 }
 
 nsresult
-CamerasParent::DispatchToVideoCaptureThread(nsRunnable *event)
+CamerasParent::DispatchToVideoCaptureThread(Runnable *event)
 {
   // Don't try to dispatch if we're already on the right thread.
   // There's a potential deadlock because the mThreadMonitor is likely
   // to be taken already.
   MOZ_ASSERT(!mVideoCaptureThread ||
              mVideoCaptureThread->thread_id() != PlatformThread::CurrentId());
 
   MonitorAutoLock lock(mThreadMonitor);
@@ -190,17 +190,17 @@ CamerasParent::DispatchToVideoCaptureThr
 void
 CamerasParent::StopVideoCapture()
 {
   LOG((__PRETTY_FUNCTION__));
   // We are called from the main thread (xpcom-shutdown) or
   // from PBackground (when the Actor shuts down).
   // Shut down the WebRTC stack (on the capture thread)
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self]() -> nsresult {
       MonitorAutoLock lock(self->mThreadMonitor);
       self->CloseEngines();
       self->mThreadMonitor.NotifyAll();
       return NS_OK;
     });
   DebugOnly<nsresult> rv = DispatchToVideoCaptureThread(webrtc_runnable);
 #ifdef DEBUG
@@ -215,17 +215,17 @@ CamerasParent::StopVideoCapture()
   while (mWebRTCAlive) {
     mThreadMonitor.Wait();
   }
   // After closing the WebRTC stack, clean up the
   // VideoCapture thread.
   if (self->mVideoCaptureThread) {
     base::Thread *thread = self->mVideoCaptureThread;
     self->mVideoCaptureThread = nullptr;
-    RefPtr<nsRunnable> threadShutdown =
+    RefPtr<Runnable> threadShutdown =
       media::NewRunnableFrom([thread]() -> nsresult {
         if (thread->IsRunning()) {
           thread->Stop();
         }
         delete thread;
         return NS_OK;
       });
     if (NS_FAILED(NS_DispatchToMainThread(threadShutdown))) {
@@ -476,17 +476,17 @@ CamerasParent::EnsureInitialized(int aEn
 // It would be nice to get rid of the code duplication here,
 // perhaps via Promises.
 bool
 CamerasParent::RecvNumberOfCaptureDevices(const int& aCapEngine)
 {
   LOG((__PRETTY_FUNCTION__));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self, aCapEngine]() -> nsresult {
       int num = -1;
       if (self->EnsureInitialized(aCapEngine)) {
         num = self->mEngines[aCapEngine].mPtrViECapture->NumberOfCaptureDevices();
       }
       RefPtr<nsIRunnable> ipc_runnable =
         media::NewRunnableFrom([self, num]() -> nsresult {
           if (self->IsShuttingDown()) {
@@ -512,17 +512,17 @@ CamerasParent::RecvNumberOfCaptureDevice
 bool
 CamerasParent::RecvNumberOfCapabilities(const int& aCapEngine,
                                         const nsCString& unique_id)
 {
   LOG((__PRETTY_FUNCTION__));
   LOG(("Getting caps for %s", unique_id.get()));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self, unique_id, aCapEngine]() -> nsresult {
       int num = -1;
       if (self->EnsureInitialized(aCapEngine)) {
         num =
           self->mEngines[aCapEngine].mPtrViECapture->NumberOfCapabilities(
             unique_id.get(),
             MediaEngineSource::kMaxUniqueIdLength);
       }
@@ -552,17 +552,17 @@ bool
 CamerasParent::RecvGetCaptureCapability(const int &aCapEngine,
                                         const nsCString& unique_id,
                                         const int& num)
 {
   LOG((__PRETTY_FUNCTION__));
   LOG(("RecvGetCaptureCapability: %s %d", unique_id.get(), num));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self, unique_id, aCapEngine, num]() -> nsresult {
       webrtc::CaptureCapability webrtcCaps;
       int error = -1;
       if (self->EnsureInitialized(aCapEngine)) {
         error = self->mEngines[aCapEngine].mPtrViECapture->GetCaptureCapability(
           unique_id.get(), MediaEngineSource::kMaxUniqueIdLength, num, webrtcCaps);
       }
       RefPtr<nsIRunnable> ipc_runnable =
@@ -600,17 +600,17 @@ CamerasParent::RecvGetCaptureCapability(
 
 bool
 CamerasParent::RecvGetCaptureDevice(const int& aCapEngine,
                                     const int& aListNumber)
 {
   LOG((__PRETTY_FUNCTION__));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self, aCapEngine, aListNumber]() -> nsresult {
       char deviceName[MediaEngineSource::kMaxDeviceNameLength];
       char deviceUniqueId[MediaEngineSource::kMaxUniqueIdLength];
       nsCString name;
       nsCString uniqueId;
       int error = -1;
       if (self->EnsureInitialized(aCapEngine)) {
           error = self->mEngines[aCapEngine].mPtrViECapture->GetCaptureDevice(aListNumber,
@@ -714,17 +714,17 @@ HasCameraPermission(const nsCString& aOr
 
 bool
 CamerasParent::RecvAllocateCaptureDevice(const int& aCapEngine,
                                          const nsCString& unique_id,
                                          const nsCString& aOrigin)
 {
   LOG(("%s: Verifying permissions for %s", __PRETTY_FUNCTION__, aOrigin.get()));
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> mainthread_runnable =
+  RefPtr<Runnable> mainthread_runnable =
     media::NewRunnableFrom([self, aCapEngine, unique_id, aOrigin]() -> nsresult {
       // Verify whether the claimed origin has received permission
       // to use the camera, either persistently or this session (one shot).
       bool allowed = HasCameraPermission(aOrigin);
       if (!allowed) {
         // Developer preference for turning off permission check.
         if (Preferences::GetBool("media.navigator.permission.disabled", false)
             || Preferences::GetBool("media.navigator.permission.fake")) {
@@ -732,17 +732,17 @@ CamerasParent::RecvAllocateCaptureDevice
           LOG(("No permission but checks are disabled or fake sources active"));
         } else {
           LOG(("No camera permission for this origin"));
         }
       }
       // After retrieving the permission (or not) on the main thread,
       // bounce to the WebRTC thread to allocate the device (or not),
       // then bounce back to the IPC thread for the reply to content.
-      RefPtr<nsRunnable> webrtc_runnable =
+      RefPtr<Runnable> webrtc_runnable =
       media::NewRunnableFrom([self, allowed, aCapEngine, unique_id]() -> nsresult {
         int numdev = -1;
         int error = -1;
         if (allowed && self->EnsureInitialized(aCapEngine)) {
           error = self->mEngines[aCapEngine].mPtrViECapture->AllocateCaptureDevice(
                     unique_id.get(), MediaEngineSource::kMaxUniqueIdLength, numdev);
         }
         RefPtr<nsIRunnable> ipc_runnable =
@@ -783,17 +783,17 @@ CamerasParent::ReleaseCaptureDevice(cons
 bool
 CamerasParent::RecvReleaseCaptureDevice(const int& aCapEngine,
                                         const int& numdev)
 {
   LOG((__PRETTY_FUNCTION__));
   LOG(("RecvReleaseCamera device nr %d", numdev));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self, aCapEngine, numdev]() -> nsresult {
       int error = self->ReleaseCaptureDevice(aCapEngine, numdev);
       RefPtr<nsIRunnable> ipc_runnable =
         media::NewRunnableFrom([self, error, numdev]() -> nsresult {
           if (self->IsShuttingDown()) {
             LOG(("In Shutdown, not Releasing"));
             return NS_ERROR_FAILURE;
           }
@@ -817,17 +817,17 @@ CamerasParent::RecvReleaseCaptureDevice(
 bool
 CamerasParent::RecvStartCapture(const int& aCapEngine,
                                 const int& capnum,
                                 const CaptureCapability& ipcCaps)
 {
   LOG((__PRETTY_FUNCTION__));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self, aCapEngine, capnum, ipcCaps]() -> nsresult {
       CallbackHelper** cbh;
       webrtc::ExternalRenderer* render;
       EngineHelper* helper = nullptr;
       int error = -1;
       if (self->EnsureInitialized(aCapEngine)) {
         cbh = self->mCallbacks.AppendElement(
           new CallbackHelper(static_cast<CaptureEngine>(aCapEngine), capnum, self));
@@ -899,17 +899,17 @@ CamerasParent::StopCapture(const int& aC
 
 bool
 CamerasParent::RecvStopCapture(const int& aCapEngine,
                                const int& capnum)
 {
   LOG((__PRETTY_FUNCTION__));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> webrtc_runnable =
+  RefPtr<Runnable> webrtc_runnable =
     media::NewRunnableFrom([self, aCapEngine, capnum]() -> nsresult {
       self->StopCapture(aCapEngine, capnum);
       return NS_OK;
     });
   nsresult rv = DispatchToVideoCaptureThread(webrtc_runnable);
   if (self->IsShuttingDown()) {
     return NS_SUCCEEDED(rv);
   } else {
@@ -964,17 +964,17 @@ CamerasParent::CamerasParent()
   LOG(("CamerasParent: %p", this));
 
   mPBackgroundThread = NS_GetCurrentThread();
   MOZ_ASSERT(mPBackgroundThread != nullptr, "GetCurrentThread failed");
 
   LOG(("Spinning up WebRTC Cameras Thread"));
 
   RefPtr<CamerasParent> self(this);
-  RefPtr<nsRunnable> threadStart =
+  RefPtr<Runnable> threadStart =
     media::NewRunnableFrom([self]() -> nsresult {
       // Register thread shutdown observer
       nsCOMPtr<nsIObserverService> obs = services::GetObserverService();
       if (NS_WARN_IF(!obs)) {
         return NS_ERROR_FAILURE;
       }
       nsresult rv =
         obs->AddObserver(self, NS_XPCOM_WILL_SHUTDOWN_OBSERVER_ID, false);
--- a/dom/media/systemservices/CamerasParent.h
+++ b/dom/media/systemservices/CamerasParent.h
@@ -124,17 +124,17 @@ protected:
   void StopCapture(const int& aCapEngine, const int& capnum);
   int ReleaseCaptureDevice(const int& aCapEngine, const int& capnum);
 
   bool SetupEngine(CaptureEngine aCapEngine);
   bool EnsureInitialized(int aEngine);
   void CloseEngines();
   void StopIPC();
   void StopVideoCapture();
-  nsresult DispatchToVideoCaptureThread(nsRunnable *event);
+  nsresult DispatchToVideoCaptureThread(Runnable *event);
 
   EngineHelper mEngines[CaptureEngine::MaxEngine];
   nsTArray<CallbackHelper*> mCallbacks;
 
   // image buffers
   mozilla::ShmemPool mShmemPool;
 
   // PBackground parent thread
--- a/dom/media/systemservices/CamerasUtils.h
+++ b/dom/media/systemservices/CamerasUtils.h
@@ -13,17 +13,17 @@
 
 #include "base/thread.h"
 
 namespace mozilla {
 namespace camera {
 
 nsresult SynchronouslyCreatePBackground();
 
-class ThreadDestructor : public nsRunnable
+class ThreadDestructor : public Runnable
 {
   DISALLOW_COPY_AND_ASSIGN(ThreadDestructor);
 
 public:
   explicit ThreadDestructor(nsIThread* aThread)
     : mThread(aThread) {}
 
   NS_IMETHOD Run() override
@@ -37,24 +37,24 @@ public:
 private:
   ~ThreadDestructor() {}
   nsCOMPtr<nsIThread> mThread;
 };
 
 class RunnableTask : public Task
 {
 public:
-  explicit RunnableTask(nsRunnable* aRunnable)
+  explicit RunnableTask(Runnable* aRunnable)
     : mRunnable(aRunnable) {}
 
   void Run() override {
     mRunnable->Run();
   }
 
 private:
   ~RunnableTask() {}
-  RefPtr<nsRunnable> mRunnable;
+  RefPtr<Runnable> mRunnable;
 };
 
 }
 }
 
 #endif // mozilla_CameraUtils_h
--- a/dom/media/systemservices/LoadMonitor.cpp
+++ b/dom/media/systemservices/LoadMonitor.cpp
@@ -89,17 +89,17 @@ LoadMonitor::Observe(nsISupports* /* aSu
                      const char16_t* /* aData */)
 {
   MOZ_ASSERT(NS_IsMainThread(), "Wrong thread!");
   MOZ_ASSERT(!strcmp("xpcom-shutdown-threads", aTopic), "Bad topic!");
   Shutdown();
   return NS_OK;
 }
 
-class LoadMonitorAddObserver : public nsRunnable
+class LoadMonitorAddObserver : public Runnable
 {
 public:
   explicit LoadMonitorAddObserver(RefPtr<LoadMonitor> loadMonitor)
   {
     mLoadMonitor = loadMonitor;
   }
 
   NS_IMETHOD Run()
@@ -114,17 +114,17 @@ public:
 
     return NS_OK;
   }
 
 private:
   RefPtr<LoadMonitor> mLoadMonitor;
 };
 
-class LoadMonitorRemoveObserver : public nsRunnable
+class LoadMonitorRemoveObserver : public Runnable
 {
 public:
   explicit LoadMonitorRemoveObserver(RefPtr<LoadMonitor> loadMonitor)
   {
     mLoadMonitor = loadMonitor;
   }
 
   NS_IMETHOD Run()
@@ -527,17 +527,17 @@ nsresult RTCLoadInfo::UpdateProcessLoad(
                 cpu_times,
                 &mProcessLoad);
 #endif
   return NS_OK;
 }
 
 // Note: This class can't be in the anonymous namespace, because then we can't
 // declare it as a friend of LoadMonitor.
-class LoadInfoCollectRunner : public nsRunnable
+class LoadInfoCollectRunner : public Runnable
 {
 public:
   LoadInfoCollectRunner(RefPtr<LoadMonitor> loadMonitor,
                         RefPtr<RTCLoadInfo> loadInfo,
                         nsIThread *loadInfoThread)
     : mThread(loadInfoThread),
       mLoadUpdateInterval(loadMonitor->mLoadUpdateInterval),
       mLoadNoiseCounter(0)
--- a/dom/media/systemservices/MediaUtils.h
+++ b/dom/media/systemservices/MediaUtils.h
@@ -141,24 +141,24 @@ protected:
 private:
   ~Pledge() {};
   bool mDone;
   bool mRejected;
   ErrorType mError;
   UniquePtr<FunctorsBase> mFunctors;
 };
 
-/* media::NewRunnableFrom() - Create an nsRunnable from a lambda.
+/* media::NewRunnableFrom() - Create a Runnable from a lambda.
  * media::NewTaskFrom()     - Create a Task from a lambda.
  *
- * Passing variables (closures) to an async function is clunky with nsRunnable:
+ * Passing variables (closures) to an async function is clunky with Runnable:
  *
  *   void Foo()
  *   {
- *     class FooRunnable : public nsRunnable
+ *     class FooRunnable : public Runnable
  *     {
  *     public:
  *       FooRunnable(const Bar &aBar) : mBar(aBar) {}
  *       NS_IMETHOD Run()
  *       {
  *         // Use mBar
  *       }
  *     private:
@@ -181,17 +181,17 @@ private:
  *
  * Capture is by-copy by default, so the nsRefPtr 'bar' is safely copied for
  * access on the other thread (threadsafe refcounting in bar is assumed).
  *
  * The 'mutable' keyword is only needed for non-const access to bar.
  */
 
 template<typename OnRunType>
-class LambdaRunnable : public nsRunnable
+class LambdaRunnable : public Runnable
 {
 public:
   explicit LambdaRunnable(OnRunType&& aOnRun) : mOnRun(Move(aOnRun)) {}
 private:
   NS_IMETHODIMP
   Run()
   {
     return mOnRun();
--- a/dom/media/webaudio/AnalyserNode.cpp
+++ b/dom/media/webaudio/AnalyserNode.cpp
@@ -21,17 +21,17 @@ static_assert((CHUNK_COUNT & (CHUNK_COUN
               "CHUNK_COUNT must be power of 2 for remainder behavior");
 
 namespace dom {
 
 NS_IMPL_ISUPPORTS_INHERITED0(AnalyserNode, AudioNode)
 
 class AnalyserNodeEngine final : public AudioNodeEngine
 {
-  class TransferBuffer final : public nsRunnable
+  class TransferBuffer final : public Runnable
   {
   public:
     TransferBuffer(AudioNodeStream* aStream,
                    const AudioChunk& aChunk)
       : mStream(aStream)
       , mChunk(aChunk)
     {
     }
--- a/dom/media/webaudio/AudioBufferSourceNode.cpp
+++ b/dom/media/webaudio/AudioBufferSourceNode.cpp
@@ -767,17 +767,17 @@ AudioBufferSourceNode::Stop(double aWhen
   ns->SetStreamTimeParameter(STOP, Context(), std::max(0.0, aWhen));
 }
 
 void
 AudioBufferSourceNode::NotifyMainThreadStreamFinished()
 {
   MOZ_ASSERT(mStream->IsFinished());
 
-  class EndedEventDispatcher final : public nsRunnable
+  class EndedEventDispatcher final : public Runnable
   {
   public:
     explicit EndedEventDispatcher(AudioBufferSourceNode* aNode)
       : mNode(aNode) {}
     NS_IMETHODIMP Run() override
     {
       // If it's not safe to run scripts right now, schedule this to run later
       if (!nsContentUtils::IsSafeToRunScript()) {
--- a/dom/media/webaudio/AudioContext.cpp
+++ b/dom/media/webaudio/AudioContext.cpp
@@ -752,17 +752,17 @@ StateChangeTask::Run()
   // We have can't call Release() on the AudioContext on the MSG thread, so we
   // unref it here, on the main thread.
   mAudioContext = nullptr;
 
   return NS_OK;
 }
 
 /* This runnable allows to fire the "statechange" event */
-class OnStateChangeTask final : public nsRunnable
+class OnStateChangeTask final : public Runnable
 {
 public:
   explicit OnStateChangeTask(AudioContext* aAudioContext)
     : mAudioContext(aAudioContext)
   {}
 
   NS_IMETHODIMP
   Run() override
--- a/dom/media/webaudio/AudioContext.h
+++ b/dom/media/webaudio/AudioContext.h
@@ -86,17 +86,17 @@ private:
   RefPtr<WebCore::PeriodicWave> mSquare;
   RefPtr<WebCore::PeriodicWave> mTriangle;
   uint32_t mSampleRate;
 };
 
 
 /* This runnable allows the MSG to notify the main thread when audio is actually
  * flowing */
-class StateChangeTask final : public nsRunnable
+class StateChangeTask final : public Runnable
 {
 public:
   /* This constructor should be used when this event is sent from the main
    * thread. */
   StateChangeTask(AudioContext* aAudioContext, void* aPromise, AudioContextState aNewState);
 
   /* This constructor should be used when this event is sent from the audio
    * thread. */
--- a/dom/media/webaudio/AudioDestinationNode.cpp
+++ b/dom/media/webaudio/AudioDestinationNode.cpp
@@ -117,17 +117,17 @@ public:
   bool IsActive() const override
   {
     // Keep processing to track stream time, which is used for all timelines
     // associated with the same AudioContext.
     return true;
   }
 
 
-  class OnCompleteTask final : public nsRunnable
+  class OnCompleteTask final : public Runnable
   {
   public:
     OnCompleteTask(AudioContext* aAudioContext, AudioBuffer* aRenderedBuffer)
       : mAudioContext(aAudioContext)
       , mRenderedBuffer(aRenderedBuffer)
     {}
 
     NS_IMETHOD Run() override
@@ -193,17 +193,17 @@ private:
   uint32_t mWriteIndex;
   uint32_t mNumberOfChannels;
   // How many frames the OfflineAudioContext intends to produce.
   uint32_t mLength;
   float mSampleRate;
   bool mBufferAllocated;
 };
 
-class InputMutedRunnable final : public nsRunnable
+class InputMutedRunnable final : public Runnable
 {
 public:
   InputMutedRunnable(AudioNodeStream* aStream,
                      bool aInputMuted)
     : mStream(aStream)
     , mInputMuted(aInputMuted)
   {
   }
--- a/dom/media/webaudio/AudioNode.cpp
+++ b/dom/media/webaudio/AudioNode.cpp
@@ -302,17 +302,17 @@ AudioNode::Disconnect(uint32_t aOutput, 
   WEB_AUDIO_API_LOG("%f: %s %u Disconnect()", Context()->CurrentTime(),
                     NodeType(), Id());
 
   // An upstream node may be starting to play on the graph thread, and the
   // engine for a downstream node may be sending a PlayingRefChangeHandler
   // ADDREF message to this (main) thread.  Wait for a round trip before
   // releasing nodes, to give engines receiving sound now time to keep their
   // nodes alive.
-  class RunnableRelease final : public nsRunnable
+  class RunnableRelease final : public Runnable
   {
   public:
     explicit RunnableRelease(already_AddRefed<AudioNode> aNode)
       : mNode(aNode) {}
 
     NS_IMETHODIMP Run() override
     {
       mNode = nullptr;
--- a/dom/media/webaudio/DynamicsCompressorNode.cpp
+++ b/dom/media/webaudio/DynamicsCompressorNode.cpp
@@ -138,17 +138,17 @@ public:
     return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
   }
 
 private:
   void SendReductionParamToMainThread(AudioNodeStream* aStream, float aReduction)
   {
     MOZ_ASSERT(!NS_IsMainThread());
 
-    class Command final : public nsRunnable
+    class Command final : public Runnable
     {
     public:
       Command(AudioNodeStream* aStream, float aReduction)
         : mStream(aStream)
         , mReduction(aReduction)
       {
       }
 
--- a/dom/media/webaudio/MediaBufferDecoder.cpp
+++ b/dom/media/webaudio/MediaBufferDecoder.cpp
@@ -50,17 +50,17 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
 
 NS_IMPL_CYCLE_COLLECTION_TRACE_BEGIN(WebAudioDecodeJob)
 NS_IMPL_CYCLE_COLLECTION_TRACE_END
 NS_IMPL_CYCLE_COLLECTION_ROOT_NATIVE(WebAudioDecodeJob, AddRef)
 NS_IMPL_CYCLE_COLLECTION_UNROOT_NATIVE(WebAudioDecodeJob, Release)
 
 using namespace dom;
 
-class ReportResultTask final : public nsRunnable
+class ReportResultTask final : public Runnable
 {
 public:
   ReportResultTask(WebAudioDecodeJob& aDecodeJob,
                    WebAudioDecodeJob::ResultFn aFunction,
                    WebAudioDecodeJob::ErrorCode aErrorCode)
     : mDecodeJob(aDecodeJob)
     , mFunction(aFunction)
     , mErrorCode(aErrorCode)
@@ -89,17 +89,17 @@ private:
 
 enum class PhaseEnum : int
 {
   Decode,
   AllocateBuffer,
   Done
 };
 
-class MediaDecodeTask final : public nsRunnable
+class MediaDecodeTask final : public Runnable
 {
 public:
   MediaDecodeTask(const char* aContentType, uint8_t* aBuffer,
                   uint32_t aLength,
                   WebAudioDecodeJob& aDecodeJob)
     : mContentType(aContentType)
     , mBuffer(aBuffer)
     , mLength(aLength)
--- a/dom/media/webaudio/OscillatorNode.cpp
+++ b/dom/media/webaudio/OscillatorNode.cpp
@@ -528,17 +528,17 @@ OscillatorNode::Stop(double aWhen, Error
                                   Context(), std::max(0.0, aWhen));
 }
 
 void
 OscillatorNode::NotifyMainThreadStreamFinished()
 {
   MOZ_ASSERT(mStream->IsFinished());
 
-  class EndedEventDispatcher final : public nsRunnable
+  class EndedEventDispatcher final : public Runnable
   {
   public:
     explicit EndedEventDispatcher(OscillatorNode* aNode)
       : mNode(aNode) {}
     NS_IMETHOD Run() override
     {
       // If it's not safe to run scripts right now, schedule this to run later
       if (!nsContentUtils::IsSafeToRunScript()) {
--- a/dom/media/webaudio/PlayingRefChangeHandler.h
+++ b/dom/media/webaudio/PlayingRefChangeHandler.h
@@ -8,17 +8,17 @@
 #define PlayingRefChangeHandler_h__
 
 #include "nsThreadUtils.h"
 #include "AudioNodeStream.h"
 
 namespace mozilla {
 namespace dom {
 
-class PlayingRefChangeHandler final : public nsRunnable
+class PlayingRefChangeHandler final : public Runnable
 {
 public:
   enum ChangeType { ADDREF, RELEASE };
   PlayingRefChangeHandler(AudioNodeStream* aStream, ChangeType aChange)
     : mStream(aStream)
     , mChange(aChange)
   {
   }
--- a/dom/media/webaudio/ReportDecodeResultTask.h
+++ b/dom/media/webaudio/ReportDecodeResultTask.h
@@ -7,17 +7,17 @@
 #ifndef ReportDecodeResultTask_h_
 #define ReportDecodeResultTask_h_
 
 #include "mozilla/Attributes.h"
 #include "MediaBufferDecoder.h"
 
 namespace mozilla {
 
-class ReportDecodeResultTask final : public nsRunnable
+class ReportDecodeResultTask final : public Runnable
 {
 public:
   ReportDecodeResultTask(DecodeJob& aDecodeJob,
                          DecodeJob::ResultFn aFunction)
     : mDecodeJob(aDecodeJob)
     , mFunction(aFunction)
   {
     MOZ_ASSERT(aFunction);
--- a/dom/media/webaudio/ScriptProcessorNode.cpp
+++ b/dom/media/webaudio/ScriptProcessorNode.cpp
@@ -363,17 +363,17 @@ private:
     StreamTime playbackTick = mDestination->GraphTimeToStreamTime(aFrom);
     // Add the duration of the current sample
     playbackTick += WEBAUDIO_BLOCK_SIZE;
     // Add the delay caused by the main thread
     playbackTick += mSharedBuffers->DelaySoFar();
     // Compute the playback time in the coordinate system of the destination
     double playbackTime = mDestination->StreamTimeToSeconds(playbackTick);
 
-    class Command final : public nsRunnable
+    class Command final : public Runnable
     {
     public:
       Command(AudioNodeStream* aStream,
               already_AddRefed<ThreadSharedFloatArrayBufferList> aInputBuffer,
               double aPlaybackTime)
         : mStream(aStream)
         , mInputBuffer(aInputBuffer)
         , mPlaybackTime(aPlaybackTime)
--- a/dom/media/webaudio/blink/HRTFDatabaseLoader.cpp
+++ b/dom/media/webaudio/blink/HRTFDatabaseLoader.cpp
@@ -102,17 +102,17 @@ size_t HRTFDatabaseLoader::sizeOfIncludi
 
     if (m_hrtfDatabase) {
         amount += m_hrtfDatabase->sizeOfIncludingThis(aMallocSizeOf);
     }
 
     return amount;
 }
 
-class HRTFDatabaseLoader::ProxyReleaseEvent final : public nsRunnable {
+class HRTFDatabaseLoader::ProxyReleaseEvent final : public Runnable {
 public:
     explicit ProxyReleaseEvent(HRTFDatabaseLoader* loader) : mLoader(loader) {}
     NS_IMETHOD Run() override
     {
         mLoader->MainThreadRelease();
         return NS_OK;
     }
 private:
--- a/dom/media/webrtc/MediaEngineGonkVideoSource.cpp
+++ b/dom/media/webrtc/MediaEngineGonkVideoSource.cpp
@@ -559,17 +559,17 @@ MediaEngineGonkVideoSource::OnUserError(
     // Scope the monitor, since there is another monitor below and we don't want
     // unexpected deadlock.
     ReentrantMonitorAutoEnter sync(mCallbackMonitor);
     mCallbackMonitor.Notify();
   }
 
   // A main thread runnable to send error code to all queued
   // MediaEnginePhotoCallbacks.
-  class TakePhotoError : public nsRunnable {
+  class TakePhotoError : public Runnable {
   public:
     TakePhotoError(nsTArray<RefPtr<MediaEnginePhotoCallback>>& aCallbacks,
                    nsresult aRv)
       : mRv(aRv)
     {
       mCallbacks.SwapElements(aCallbacks);
     }
 
@@ -601,17 +601,17 @@ void
 MediaEngineGonkVideoSource::OnTakePictureComplete(const uint8_t* aData, uint32_t aLength, const nsAString& aMimeType)
 {
   // It needs to start preview because Gonk camera will stop preview while
   // taking picture.
   mCameraControl->StartPreview();
 
   // Create a main thread runnable to generate a blob and call all current queued
   // MediaEnginePhotoCallbacks.
-  class GenerateBlobRunnable : public nsRunnable {
+  class GenerateBlobRunnable : public Runnable {
   public:
     GenerateBlobRunnable(nsTArray<RefPtr<MediaEnginePhotoCallback>>& aCallbacks,
                          const uint8_t* aData,
                          uint32_t aLength,
                          const nsAString& aMimeType)
       : mPhotoDataLength(aLength)
     {
       mCallbacks.SwapElements(aCallbacks);
--- a/dom/media/webrtc/MediaEngineTabVideoSource.h
+++ b/dom/media/webrtc/MediaEngineTabVideoSource.h
@@ -47,31 +47,31 @@ class MediaEngineTabVideoSource : public
 
     nsresult TakePhoto(MediaEnginePhotoCallback* aCallback) override
     {
       return NS_ERROR_NOT_IMPLEMENTED;
     }
 
     void Draw();
 
-    class StartRunnable : public nsRunnable {
+    class StartRunnable : public Runnable {
     public:
       explicit StartRunnable(MediaEngineTabVideoSource *videoSource) : mVideoSource(videoSource) {}
       NS_IMETHOD Run();
       RefPtr<MediaEngineTabVideoSource> mVideoSource;
     };
 
-    class StopRunnable : public nsRunnable {
+    class StopRunnable : public Runnable {
     public:
       explicit StopRunnable(MediaEngineTabVideoSource *videoSource) : mVideoSource(videoSource) {}
       NS_IMETHOD Run();
       RefPtr<MediaEngineTabVideoSource> mVideoSource;
     };
 
-    class InitRunnable : public nsRunnable {
+    class InitRunnable : public Runnable {
     public:
       explicit InitRunnable(MediaEngineTabVideoSource *videoSource) : mVideoSource(videoSource) {}
       NS_IMETHOD Run();
       RefPtr<MediaEngineTabVideoSource> mVideoSource;
     };
 
 protected:
     ~MediaEngineTabVideoSource() {}
--- a/dom/media/webspeech/recognition/PocketSphinxSpeechRecognitionService.cpp
+++ b/dom/media/webspeech/recognition/PocketSphinxSpeechRecognitionService.cpp
@@ -25,17 +25,17 @@ extern "C" {
 #include "sphinxbase/sphinx_config.h"
 #include "sphinxbase/jsgf.h"
 }
 
 namespace mozilla {
 
 using namespace dom;
 
-class DecodeResultTask : public nsRunnable
+class DecodeResultTask : public Runnable
 {
 public:
   DecodeResultTask(const nsString& hypstring,
                    float64 confidence,
                    WeakPtr<dom::SpeechRecognition> recognition)
       : mResult(hypstring),
         mConfidence(confidence),
         mRecognition(recognition),
@@ -80,17 +80,17 @@ public:
 
 private:
   nsString mResult;
   float64 mConfidence;
   WeakPtr<dom::SpeechRecognition> mRecognition;
   nsCOMPtr<nsIThread> mWorkerThread;
 };
 
-class DecodeTask : public nsRunnable
+class DecodeTask : public Runnable
 {
 public:
   DecodeTask(WeakPtr<dom::SpeechRecognition> recogntion,
              const nsTArray<int16_t>& audiovector, ps_decoder_t* ps)
       : mRecognition(recogntion), mAudiovector(audiovector), mPs(ps)
   {
   }
 
--- a/dom/media/webspeech/recognition/SpeechRecognition.h
+++ b/dom/media/webspeech/recognition/SpeechRecognition.h
@@ -278,17 +278,17 @@ private:
   uint32_t mMaxAlternatives;
 
   void ProcessTestEventRequest(nsISupports* aSubject, const nsAString& aEventName);
 
   const char* GetName(FSMState aId);
   const char* GetName(SpeechEvent* aId);
 };
 
-class SpeechEvent : public nsRunnable
+class SpeechEvent : public Runnable
 {
 public:
   SpeechEvent(SpeechRecognition* aRecognition, SpeechRecognition::EventType aType)
   : mAudioSegment(0)
   , mRecognitionResultList(0)
   , mError(0)
   , mRecognition(aRecognition)
   , mType(aType)
--- a/dom/media/webspeech/synth/cocoa/OSXSpeechSynthesizerService.mm
+++ b/dom/media/webspeech/synth/cocoa/OSXSpeechSynthesizerService.mm
@@ -203,17 +203,17 @@ struct OSXVoice
   }
 
   nsString mUri;
   nsString mName;
   nsString mLocale;
   bool mIsDefault;
 };
 
-class RegisterVoicesRunnable final : public nsRunnable
+class RegisterVoicesRunnable final : public Runnable
 {
 public:
   RegisterVoicesRunnable(OSXSpeechSynthesizerService* aSpeechService,
                          nsTArray<OSXVoice>& aList)
     : mSpeechService(aSpeechService)
     , mVoices(aList)
   {
   }
@@ -251,17 +251,17 @@ RegisterVoicesRunnable::Run()
     }
   }
 
   registry->NotifyVoicesChanged();
 
   return NS_OK;
 }
 
-class EnumVoicesRunnable final : public nsRunnable
+class EnumVoicesRunnable final : public Runnable
 {
 public:
   explicit EnumVoicesRunnable(OSXSpeechSynthesizerService* aSpeechService)
     : mSpeechService(aSpeechService)
   {
   }
 
   NS_IMETHOD Run() override;
--- a/dom/media/webspeech/synth/pico/nsPicoService.cpp
+++ b/dom/media/webspeech/synth/pico/nsPicoService.cpp
@@ -205,17 +205,17 @@ public:
 
   // Speaker resource file
   nsCString mSgFile;
 
 private:
     ~PicoVoice() {}
 };
 
-class PicoCallbackRunnable : public nsRunnable,
+class PicoCallbackRunnable : public Runnable,
                              public nsISpeechTaskCallback
 {
   friend class PicoSynthDataRunnable;
 
 public:
   PicoCallbackRunnable(const nsAString& aText, PicoVoice* aVoice,
                        float aRate, float aPitch, nsISpeechTask* aTask,
                        nsPicoService* aService)
@@ -256,19 +256,19 @@ private:
   // a strong reference to this voice.
   PicoVoice* mVoice;
 
   // By holding a strong reference to the service we guarantee that it won't be
   // destroyed before this runnable.
   RefPtr<nsPicoService> mService;
 };
 
-NS_IMPL_ISUPPORTS_INHERITED(PicoCallbackRunnable, nsRunnable, nsISpeechTaskCallback)
+NS_IMPL_ISUPPORTS_INHERITED(PicoCallbackRunnable, Runnable, nsISpeechTaskCallback)
 
-// nsRunnable
+// Runnable
 
 NS_IMETHODIMP
 PicoCallbackRunnable::Run()
 {
   MOZ_ASSERT(!NS_IsMainThread());
   PicoApi::pico_Status status = 0;
 
   if (mService->CurrentVoice() != mVoice) {
@@ -337,17 +337,17 @@ PicoCallbackRunnable::Run()
 
   return NS_OK;
 }
 
 void
 PicoCallbackRunnable::DispatchSynthDataRunnable(
   already_AddRefed<SharedBuffer>&& aBuffer, size_t aBufferSize)
 {
-  class PicoSynthDataRunnable final : public nsRunnable
+  class PicoSynthDataRunnable final : public Runnable
   {
   public:
     PicoSynthDataRunnable(already_AddRefed<SharedBuffer>& aBuffer,
                           size_t aBufferSize, bool aFirstData,
                           PicoCallbackRunnable* aCallback)
       : mBuffer(aBuffer)
       , mBufferSize(aBufferSize)
       , mFirstData(aFirstData)
--- a/dom/media/webspeech/synth/test/nsFakeSynthServices.cpp
+++ b/dom/media/webspeech/synth/test/nsFakeSynthServices.cpp
@@ -133,17 +133,17 @@ private:
 
 NS_IMPL_ISUPPORTS(FakeDirectAudioSynth, nsISpeechService)
 
 NS_IMETHODIMP
 FakeDirectAudioSynth::Speak(const nsAString& aText, const nsAString& aUri,
                             float aVolume, float aRate, float aPitch,
                             nsISpeechTask* aTask)
 {
-  class Runnable final : public nsRunnable
+  class Runnable final : public mozilla::Runnable
   {
   public:
     Runnable(nsISpeechTask* aTask, const nsAString& aText) :
       mTask(aTask), mText(aText)
     {
     }
 
     NS_IMETHOD Run() override
@@ -196,17 +196,17 @@ private:
 
 NS_IMPL_ISUPPORTS(FakeIndirectAudioSynth, nsISpeechService)
 
 NS_IMETHODIMP
 FakeIndirectAudioSynth::Speak(const nsAString& aText, const nsAString& aUri,
                               float aVolume, float aRate, float aPitch,
                               nsISpeechTask* aTask)
 {
-  class DispatchStart final : public nsRunnable
+  class DispatchStart final : public Runnable
   {
   public:
     explicit DispatchStart(nsISpeechTask* aTask) :
       mTask(aTask)
     {
     }
 
     NS_IMETHOD Run() override
@@ -215,17 +215,17 @@ FakeIndirectAudioSynth::Speak(const nsAS
 
       return NS_OK;
     }
 
   private:
     nsCOMPtr<nsISpeechTask> mTask;
   };
 
-  class DispatchEnd final : public nsRunnable
+  class DispatchEnd final : public Runnable
   {
   public:
     DispatchEnd(nsISpeechTask* aTask, const nsAString& aText) :
       mTask(aTask), mText(aText)
     {
     }
 
     NS_IMETHOD Run() override
@@ -235,17 +235,17 @@ FakeIndirectAudioSynth::Speak(const nsAS
       return NS_OK;
     }
 
   private:
     nsCOMPtr<nsISpeechTask> mTask;
     nsString mText;
   };
 
-  class DispatchError final : public nsRunnable
+  class DispatchError final : public Runnable
   {
   public:
     DispatchError(nsISpeechTask* aTask, const nsAString& aText) :
       mTask(aTask), mText(aText)
     {
     }
 
     NS_IMETHOD Run() override
--- a/dom/network/UDPSocket.cpp
+++ b/dom/network/UDPSocket.cpp
@@ -536,17 +536,17 @@ UDPSocket::Init(const nsString& aLocalAd
     return rv.StealNSResult();
   }
 
   mClosed = Promise::Create(global, rv);
   if (NS_WARN_IF(rv.Failed())) {
     return rv.StealNSResult();
   }
 
-  class OpenSocketRunnable final : public nsRunnable
+  class OpenSocketRunnable final : public Runnable
   {
   public:
     explicit OpenSocketRunnable(UDPSocket* aSocket) : mSocket(aSocket)
     { }
 
     NS_IMETHOD Run() override
     {
       MOZ_ASSERT(mSocket);
--- a/dom/notification/DesktopNotification.cpp
+++ b/dom/notification/DesktopNotification.cpp
@@ -22,17 +22,17 @@
 
 namespace mozilla {
 namespace dom {
 
 /*
  * Simple Request
  */
 class DesktopNotificationRequest : public nsIContentPermissionRequest
-                                 , public nsRunnable
+                                 , public Runnable
 {
   virtual ~DesktopNotificationRequest()
   {
   }
 
   nsCOMPtr<nsIContentPermissionRequester> mRequester;
 public:
   NS_DECL_ISUPPORTS_INHERITED
@@ -269,17 +269,17 @@ DesktopNotificationCenter::WrapObject(JS
 {
   return DesktopNotificationCenterBinding::Wrap(aCx, this, aGivenProto);
 }
 
 /* ------------------------------------------------------------------------ */
 /* DesktopNotificationRequest                                               */
 /* ------------------------------------------------------------------------ */
 
-NS_IMPL_ISUPPORTS_INHERITED(DesktopNotificationRequest, nsRunnable,
+NS_IMPL_ISUPPORTS_INHERITED(DesktopNotificationRequest, Runnable,
                             nsIContentPermissionRequest)
 
 NS_IMETHODIMP
 DesktopNotificationRequest::GetPrincipal(nsIPrincipal * *aRequestingPrincipal)
 {
   if (!mDesktopNotification) {
     return NS_ERROR_NOT_INITIALIZED;
   }
--- a/dom/notification/Notification.cpp
+++ b/dom/notification/Notification.cpp
@@ -195,17 +195,17 @@ NS_IMPL_CYCLE_COLLECTING_ADDREF(Notifica
 NS_IMPL_CYCLE_COLLECTING_RELEASE(NotificationStorageCallback)
 NS_IMPL_CYCLE_COLLECTION(NotificationStorageCallback, mWindow, mPromise);
 
 NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(NotificationStorageCallback)
   NS_INTERFACE_MAP_ENTRY(nsINotificationStorageCallback)
   NS_INTERFACE_MAP_ENTRY(nsISupports)
 NS_INTERFACE_MAP_END
 
-class NotificationGetRunnable final : public nsRunnable
+class NotificationGetRunnable final : public Runnable
 {
   const nsString mOrigin;
   const nsString mTag;
   nsCOMPtr<nsINotificationStorageCallback> mCallback;
 public:
   NotificationGetRunnable(const nsAString& aOrigin,
                           const nsAString& aTag,
                           nsINotificationStorageCallback* aCallback)
@@ -305,17 +305,17 @@ public:
 
   NotificationPermission
   GetPermission()
   {
     return mPermission;
   }
 };
 
-class FocusWindowRunnable final : public nsRunnable
+class FocusWindowRunnable final : public Runnable
 {
   nsMainThreadPtrHandle<nsPIDOMWindowInner> mWindow;
 public:
   explicit FocusWindowRunnable(const nsMainThreadPtrHandle<nsPIDOMWindowInner>& aWindow)
     : mWindow(aWindow)
   { }
 
   NS_IMETHOD
@@ -515,17 +515,17 @@ public:
   Notification*
   GetNotification()
   {
     MOZ_ASSERT(Initialized());
     return mNotification;
   }
 };
 
-class NotificationTask : public nsRunnable
+class NotificationTask : public Runnable
 {
 public:
   enum NotificationAction {
     eShow,
     eClose
   };
 
   NotificationTask(UniquePtr<NotificationRef> aRef, NotificationAction aAction)
@@ -538,17 +538,18 @@ protected:
   virtual ~NotificationTask() {}
 
   UniquePtr<NotificationRef> mNotificationRef;
   NotificationAction mAction;
 };
 
 uint32_t Notification::sCount = 0;
 
-NS_IMPL_CYCLE_COLLECTION(NotificationPermissionRequest, mWindow, mPromise)
+NS_IMPL_CYCLE_COLLECTION(NotificationPermissionRequest, mWindow, mPromise,
+                                                        mCallback)
 
 NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(NotificationPermissionRequest)
   NS_INTERFACE_MAP_ENTRY(nsIContentPermissionRequest)
   NS_INTERFACE_MAP_ENTRY(nsIRunnable)
   NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIContentPermissionRequest)
 NS_INTERFACE_MAP_END
 
 NS_IMPL_CYCLE_COLLECTING_ADDREF(NotificationPermissionRequest)
@@ -2180,17 +2181,17 @@ public:
 
 private:
   ~WorkerGetCallback()
   {}
 };
 
 NS_IMPL_ISUPPORTS(WorkerGetCallback, nsINotificationStorageCallback)
 
-class WorkerGetRunnable final : public nsRunnable
+class WorkerGetRunnable final : public Runnable
 {
   RefPtr<PromiseWorkerProxy> mPromiseProxy;
   const nsString mTag;
   const nsString mScope;
 public:
   WorkerGetRunnable(PromiseWorkerProxy* aProxy,
                     const nsAString& aTag,
                     const nsAString& aScope)
--- a/dom/permission/Permissions.cpp
+++ b/dom/permission/Permissions.cpp
@@ -39,57 +39,34 @@ JSObject*
 Permissions::WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto)
 {
   return PermissionsBinding::Wrap(aCx, this, aGivenProto);
 }
 
 namespace {
 
 already_AddRefed<PermissionStatus>
-CreatePushPermissionStatus(JSContext* aCx,
-                           JS::Handle<JSObject*> aPermission,
-                           nsPIDOMWindowInner* aWindow,
-                           ErrorResult& aRv)
-{
-  PushPermissionDescriptor permission;
-  JS::Rooted<JS::Value> value(aCx, JS::ObjectOrNullValue(aPermission));
-  if (NS_WARN_IF(!permission.Init(aCx, value))) {
-    aRv.NoteJSContextException(aCx);
-    return nullptr;
-  }
-
-  if (permission.mUserVisibleOnly) {
-    aRv.Throw(NS_ERROR_NOT_IMPLEMENTED);
-    return nullptr;
-  }
-
-  return PermissionStatus::Create(aWindow, permission.mName, aRv);
-}
-
-already_AddRefed<PermissionStatus>
 CreatePermissionStatus(JSContext* aCx,
                        JS::Handle<JSObject*> aPermission,
                        nsPIDOMWindowInner* aWindow,
                        ErrorResult& aRv)
 {
   PermissionDescriptor permission;
   JS::Rooted<JS::Value> value(aCx, JS::ObjectOrNullValue(aPermission));
   if (NS_WARN_IF(!permission.Init(aCx, value))) {
     aRv.NoteJSContextException(aCx);
     return nullptr;
   }
 
   switch (permission.mName) {
     case PermissionName::Geolocation:
     case PermissionName::Notifications:
+    case PermissionName::Push:
       return PermissionStatus::Create(aWindow, permission.mName, aRv);
 
-    case PermissionName::Push:
-      return CreatePushPermissionStatus(aCx, aPermission, aWindow, aRv);
-
     default:
       MOZ_ASSERT_UNREACHABLE("Unhandled type");
       aRv.Throw(NS_ERROR_NOT_IMPLEMENTED);
       return nullptr;
   }
 }
 
 } // namespace
--- a/dom/permission/tests/test_permissions_api.html
+++ b/dom/permission/tests/test_permissions_api.html
@@ -53,22 +53,16 @@ function revokePermissions(action) {
 function revokeUnsupportedPermissions() {
   return Promise.all(UNSUPPORTED_PERMISSIONS.map(name =>
     navigator.permissions.revoke({ name: name }).then(
       result => ok(false, `revoke should not have resolved for '${name}'`),
       error => is(error.name, 'TypeError', `revoke should have thrown TypeError for '${name}'`))
   ));
 }
 
-function revokeUserVisibleOnlyPushPermission() {
-  return navigator.permissions.revoke({ name: 'push', userVisibleOnly: true }).then(
-    result => ok(false, `revoke should not have resolved for userVisibleOnly push`),
-    error => ok(true, `revoke should have rejected for userVisibleOnly push`));
-}
-
 function checkPermissions(state) {
   return Promise.all(PERMISSIONS.map(x => {
     return navigator.permissions.query({ name: x.name }).then(
       result => is(result.state, state, `correct state for '${x.name}'`),
       error => ok(false, `query should not have rejected for '${x.name}'`));
   }));
 }
 
@@ -78,22 +72,16 @@ function checkUnsupportedPermissions() {
       result => ok(false, `query should not have resolved for '${name}'`),
       error => {
         is(error.name, 'TypeError',
            `query should have thrown TypeError for '${name}'`);
       });
   }));
 }
 
-function checkUserVisibleOnlyPushPermission() {
-  return navigator.permissions.query({ name: 'push', userVisibleOnly: true }).then(
-    result => ok(false, `query should not have resolved for userVisibleOnly push`),
-    error => ok(true, `query should have rejected for userVisibleOnly push`));
-}
-
 function promiseStateChanged(name, state) {
   return navigator.permissions.query({ name }).then(
     status => {
       return new Promise((resolve, reject) => {
         status.onchange = () => {
           status.onchange = null;
           is(status.state, state, `state changed for '${name}'`);
           resolve();
@@ -127,29 +115,27 @@ function testInvalidQuery() {
 function testInvalidRevoke() {
   navigator.permissions.revoke({ name: 'invalid' }).then(
     result => ok(false, 'invalid revoke should not have resolved'),
     error => ok(true, 'invalid revoke should have rejected'));
 }
 
 function runTests() {
   checkUnsupportedPermissions()
-    .then(checkUserVisibleOnlyPushPermission)
     .then(() => setPermissions(UNKNOWN_ACTION))
     .then(() => checkPermissions('prompt'))
     .then(() => setPermissions(PROMPT_ACTION))
     .then(() => checkPermissions('prompt'))
     .then(() => setPermissions(ALLOW_ACTION))
     .then(() => checkPermissions('granted'))
     .then(() => setPermissions(DENY_ACTION))
     .then(() => checkPermissions('denied'))
     .then(testStatusOnChange)
     .then(testInvalidQuery)
     .then(revokeUnsupportedPermissions)
-    .then(revokeUserVisibleOnlyPushPermission)
     .then(revokePermissions)
     .then(() => checkPermissions('prompt'))
     .then(testInvalidRevoke)
     .then(SimpleTest.finish)
     .catch ((e) => {
       ok(false, 'Unexpected error ' + e);
       SimpleTest.finish();
     });
--- a/dom/plugins/base/android/ANPAudio.cpp
+++ b/dom/plugins/base/android/ANPAudio.cpp
@@ -102,17 +102,17 @@ struct ANPAudioTrack {
 
   void* user;
   ANPAudioCallbackProc proc;
   ANPSampleFormat format;
 
   ANPAudioTrack() : lock("ANPAudioTrack") { }
 };
 
-class AudioRunnable : public nsRunnable
+class AudioRunnable : public mozilla::Runnable
 {
 public:
   NS_DECL_NSIRUNNABLE
 
   AudioRunnable(ANPAudioTrack* aAudioTrack) {
     mTrack = aAudioTrack;
   }
 
--- a/dom/plugins/base/nsNPAPIPlugin.cpp
+++ b/dom/plugins/base/nsNPAPIPlugin.cpp
@@ -472,17 +472,17 @@ MakeNewNPAPIStreamInternal(NPP npp, cons
 #if defined(MOZ_MEMORY_WINDOWS)
 extern "C" size_t malloc_usable_size(const void *ptr);
 #endif
 
 namespace {
 
 static char *gNPPException;
 
-class nsPluginThreadRunnable : public nsRunnable,
+class nsPluginThreadRunnable : public Runnable,
                                public PRCList
 {
 public:
   nsPluginThreadRunnable(NPP instance, PluginThreadCallback func,
                          void *userData);
   virtual ~nsPluginThreadRunnable();
 
   NS_IMETHOD Run();
--- a/dom/plugins/base/nsNPAPIPluginInstance.cpp
+++ b/dom/plugins/base/nsNPAPIPluginInstance.cpp
@@ -60,17 +60,17 @@ using namespace mozilla::dom;
 #include "SurfaceTypes.h"
 #include "EGLUtils.h"
 
 using namespace mozilla;
 using namespace mozilla::gl;
 
 typedef nsNPAPIPluginInstance::VideoInfo VideoInfo;
 
-class PluginEventRunnable : public nsRunnable
+class PluginEventRunnable : public Runnable
 {
 public:
   PluginEventRunnable(nsNPAPIPluginInstance* instance, ANPEvent* event)
     : mInstance(instance), mEvent(*event), mCanceled(false) {}
 
   virtual nsresult Run() {
     if (mCanceled)
       return NS_OK;
@@ -1634,17 +1634,17 @@ nsNPAPIPluginInstance::FinalizeAsyncSurf
 void
 nsNPAPIPluginInstance::SetCurrentAsyncSurface(NPAsyncSurface *surface, NPRect *changed)
 {
   if (mOwner) {
     mOwner->SetCurrentAsyncSurface(surface, changed);
   }
 }
 
-class CarbonEventModelFailureEvent : public nsRunnable {
+class CarbonEventModelFailureEvent : public Runnable {
 public:
   nsCOMPtr<nsIContent> mContent;
 
   explicit CarbonEventModelFailureEvent(nsIContent* aContent)
     : mContent(aContent)
   {}
 
   ~CarbonEventModelFailureEvent() {}
--- a/dom/plugins/base/nsPluginHost.cpp
+++ b/dom/plugins/base/nsPluginHost.cpp
@@ -1399,17 +1399,17 @@ nsPluginHost::GetPluginForContentProcess
     pluginTag->mContentProcessRunningCount++;
     NS_ADDREF(*aPlugin = pluginTag->mPlugin);
     return NS_OK;
   }
 
   return NS_ERROR_FAILURE;
 }
 
-class nsPluginUnloadRunnable : public nsRunnable
+class nsPluginUnloadRunnable : public Runnable
 {
 public:
   explicit nsPluginUnloadRunnable(uint32_t aPluginId) : mPluginId(aPluginId) {}
 
   NS_IMETHOD Run()
   {
     RefPtr<nsPluginHost> host = nsPluginHost::GetInst();
     if (!host) {
@@ -4175,17 +4175,17 @@ nsPluginHost::DestroyRunningInstances(ns
         objectContent->PluginDestroyed();
       }
     }
   }
 }
 
 // Runnable that does an async destroy of a plugin.
 
-class nsPluginDestroyRunnable : public nsRunnable,
+class nsPluginDestroyRunnable : public Runnable,
                                 public PRCList
 {
 public:
   explicit nsPluginDestroyRunnable(nsNPAPIPluginInstance *aInstance)
     : mInstance(aInstance)
   {
     PR_INIT_CLIST(this);
     PR_APPEND_LINK(this, &sRunnableListHead);
--- a/dom/plugins/base/nsPluginInstanceOwner.cpp
+++ b/dom/plugins/base/nsPluginInstanceOwner.cpp
@@ -124,17 +124,17 @@ public:
   void Destroy(nsIContent* aContent);
 
   nsEventStatus ProcessEvent(const WidgetGUIEvent& anEvent)
   {
     return nsEventStatus_eConsumeNoDefault;
   }
 };
 
-class AsyncPaintWaitEvent : public nsRunnable
+class AsyncPaintWaitEvent : public Runnable
 {
 public:
   AsyncPaintWaitEvent(nsIContent* aContent, bool aFinished) :
     mContent(aContent), mFinished(aFinished)
   {
   }
 
   NS_IMETHOD Run()
--- a/dom/plugins/base/nsPluginNativeWindowWin.cpp
+++ b/dom/plugins/base/nsPluginNativeWindowWin.cpp
@@ -41,17 +41,17 @@ using namespace mozilla;
 #define WM_USER_FLASH WM_USER+1
 static UINT sWM_FLASHBOUNCEMSG = 0;
 
 typedef nsTWeakRef<class nsPluginNativeWindowWin> PluginWindowWeakRef;
 
 /**
  *  PLEvent handling code
  */
-class PluginWindowEvent : public nsRunnable {
+class PluginWindowEvent : public Runnable {
 public:
   PluginWindowEvent();
   void Init(const PluginWindowWeakRef &ref, HWND hWnd, UINT msg, WPARAM wParam,
             LPARAM lParam);
   void Clear();
   HWND   GetWnd()    { return mWnd; };
   UINT   GetMsg()    { return mMsg; };
   WPARAM GetWParam() { return mWParam; };
@@ -154,17 +154,17 @@ static bool ProcessFlashMessageDelayed(n
   nsCOMPtr<nsIRunnable> pwe = aWin->GetPluginWindowEvent(hWnd, msg, wParam, lParam);
   if (pwe) {
     NS_DispatchToCurrentThread(pwe);
     return true;
   }
   return false;
 }
 
-class nsDelayedPopupsEnabledEvent : public nsRunnable
+class nsDelayedPopupsEnabledEvent : public Runnable
 {
 public:
   nsDelayedPopupsEnabledEvent(nsNPAPIPluginInstance *inst)
     : mInst(inst)
   {}
 
   NS_DECL_NSIRUNNABLE
 
--- a/dom/plugins/ipc/PluginHangUIParent.cpp
+++ b/dom/plugins/ipc/PluginHangUIParent.cpp
@@ -28,17 +28,17 @@
 using base::ProcessHandle;
 
 using mozilla::widget::WidgetUtils;
 
 using std::string;
 using std::vector;
 
 namespace {
-class nsPluginHangUITelemetry : public nsRunnable
+class nsPluginHangUITelemetry : public mozilla::Runnable
 {
 public:
   nsPluginHangUITelemetry(int aResponseCode, int aDontAskCode,
                           uint32_t aResponseTimeMs, uint32_t aTimeoutMs)
     : mResponseCode(aResponseCode),
       mDontAskCode(aDontAskCode),
       mResponseTimeMs(aResponseTimeMs),
       mTimeoutMs(aTimeoutMs)
--- a/dom/plugins/ipc/PluginMessageUtils.cpp
+++ b/dom/plugins/ipc/PluginMessageUtils.cpp
@@ -14,17 +14,17 @@
 #include "PluginScriptableObjectChild.h"
 
 using std::string;
 
 using mozilla::ipc::MessageChannel;
 
 namespace {
 
-class DeferNPObjectReleaseRunnable : public nsRunnable
+class DeferNPObjectReleaseRunnable : public mozilla::Runnable
 {
 public:
   DeferNPObjectReleaseRunnable(const NPNetscapeFuncs* f, NPObject* o)
     : mFuncs(f)
     , mObject(o)
   {
     NS_ASSERTION(o, "no release null objects");
   }
--- a/dom/presentation/tests/mochitest/PresentationSessionChromeScript.js
+++ b/dom/presentation/tests/mochitest/PresentationSessionChromeScript.js
@@ -4,16 +4,19 @@
 'use strict';
 
 const { classes: Cc, interfaces: Ci, manager: Cm, utils: Cu, results: Cr } = Components;
 
 Cu.import('resource://gre/modules/XPCOMUtils.jsm');
 Cu.import('resource://gre/modules/Services.jsm');
 Cu.import('resource://gre/modules/Timer.jsm');
 
+const uuidGenerator = Cc["@mozilla.org/uuid-generator;1"]
+                      .getService(Ci.nsIUUIDGenerator);
+
 function registerMockedFactory(contractId, mockedClassId, mockedFactory) {
   var originalClassId, originalFactory;
 
   var registrar = Cm.QueryInterface(Ci.nsIComponentRegistrar);
   if (!registrar.isCIDRegistered(mockedClassId)) {
     try {
       originalClassId = registrar.contractIDToCID(contractId);
       originalFactory = Cm.getClassObject(Cc[contractId], Ci.nsIFactory);
@@ -36,17 +39,17 @@ function registerMockedFactory(contractI
 
 function registerOriginalFactory(contractId, mockedClassId, mockedFactory, originalClassId, originalFactory) {
   if (originalFactory) {
     registrar.unregisterFactory(mockedClassId, mockedFactory);
     registrar.registerFactory(originalClassId, "", contractId, originalFactory);
   }
 }
 
-const sessionId = 'test-session-id';
+const sessionId = 'test-session-id-' + uuidGenerator.generateUUID().toString();
 
 const address = Cc["@mozilla.org/supports-cstring;1"]
                   .createInstance(Ci.nsISupportsCString);
 address.data = "127.0.0.1";
 const addresses = Cc["@mozilla.org/array;1"].createInstance(Ci.nsIMutableArray);
 addresses.appendElement(address, false);
 
 const mockedChannelDescription = {
@@ -325,18 +328,16 @@ const mockedRequestUIGlue = {
   },
   sendRequest: function(aUrl, aSessionId) {
     sendAsyncMessage('receiver-launching', aSessionId);
     return requestPromise;
   },
 };
 
 // Register mocked factories.
-const uuidGenerator = Cc["@mozilla.org/uuid-generator;1"]
-                      .getService(Ci.nsIUUIDGenerator);
 const originalFactoryData = [];
 originalFactoryData.push(registerMockedFactory("@mozilla.org/presentation-device/prompt;1",
                                                uuidGenerator.generateUUID(),
                                                mockedDevicePrompt));
 originalFactoryData.push(registerMockedFactory("@mozilla.org/network/server-socket;1",
                                                uuidGenerator.generateUUID(),
                                                mockedServerSocket));
 originalFactoryData.push(registerMockedFactory("@mozilla.org/presentation/presentationtcpsessiontransport;1",
--- a/dom/promise/Promise.cpp
+++ b/dom/promise/Promise.cpp
@@ -49,17 +49,17 @@ namespace {
 // Generator used by Promise::GetID.
 Atomic<uintptr_t> gIDGenerator(0);
 } // namespace
 
 using namespace workers;
 
 #ifndef SPIDERMONKEY_PROMISE
 // This class processes the promise's callbacks with promise's result.
-class PromiseReactionJob final : public nsRunnable
+class PromiseReactionJob final : public Runnable
 {
 public:
   PromiseReactionJob(Promise* aPromise,
                      PromiseCallback* aCallback,
                      const JS::Value& aValue)
     : mPromise(aPromise)
     , mCallback(aCallback)
     , mValue(CycleCollectedJSRuntime::Get()->Runtime(), aValue)
@@ -175,17 +175,17 @@ GetPromise(JSContext* aCx, JS::Handle<JS
   Promise* promise;
   UNWRAP_OBJECT(Promise, &promiseVal.toObject(), promise);
   return promise;
 }
 } // namespace
 
 // Runnable to resolve thenables.
 // Equivalent to the specification's ResolvePromiseViaThenableTask.
-class PromiseResolveThenableJob final : public nsRunnable
+class PromiseResolveThenableJob final : public Runnable
 {
 public:
   PromiseResolveThenableJob(Promise* aPromise,
                             JS::Handle<JSObject*> aThenable,
                             PromiseInit* aThen)
     : mPromise(aPromise)
     , mThenable(CycleCollectedJSRuntime::Get()->Runtime(), aThenable)
     , mThen(aThen)
--- a/dom/push/PushManager.cpp
+++ b/dom/push/PushManager.cpp
@@ -257,17 +257,17 @@ protected:
 
 private:
   RefPtr<PromiseWorkerProxy> mProxy;
   nsString mScope;
 };
 
 NS_IMPL_ISUPPORTS(GetSubscriptionCallback, nsIPushSubscriptionCallback)
 
-class GetSubscriptionRunnable final : public nsRunnable
+class GetSubscriptionRunnable final : public Runnable
 {
 public:
   GetSubscriptionRunnable(PromiseWorkerProxy* aProxy,
                           const nsAString& aScope,
                           PushManager::SubscriptionAction aAction,
                           nsTArray<uint8_t>&& aAppServerKey)
     : mProxy(aProxy)
     , mScope(aScope)
@@ -388,17 +388,17 @@ private:
   ~PermissionResultRunnable()
   {}
 
   RefPtr<PromiseWorkerProxy> mProxy;
   nsresult mStatus;
   PushPermissionState mState;
 };
 
-class PermissionStateRunnable final : public nsRunnable
+class PermissionStateRunnable final : public Runnable
 {
 public:
   explicit PermissionStateRunnable(PromiseWorkerProxy* aProxy)
     : mProxy(aProxy)
   {}
 
   NS_IMETHOD
   Run() override
--- a/dom/push/PushServiceWebSocket.jsm
+++ b/dom/push/PushServiceWebSocket.jsm
@@ -19,36 +19,29 @@ Cu.import("resource://gre/modules/XPCOMU
 
 const {PushDB} = Cu.import("resource://gre/modules/PushDB.jsm");
 const {PushRecord} = Cu.import("resource://gre/modules/PushRecord.jsm");
 const {
   PushCrypto,
   getCryptoParams,
 } = Cu.import("resource://gre/modules/PushCrypto.jsm");
 
-XPCOMUtils.defineLazyServiceGetter(this, "gDNSService",
-                                   "@mozilla.org/network/dns-service;1",
-                                   "nsIDNSService");
-
 if (AppConstants.MOZ_B2G) {
   XPCOMUtils.defineLazyServiceGetter(this, "gPowerManagerService",
                                      "@mozilla.org/power/powermanagerservice;1",
                                      "nsIPowerManagerService");
 }
 
-var threadManager = Cc["@mozilla.org/thread-manager;1"]
-                      .getService(Ci.nsIThreadManager);
-
 const kPUSHWSDB_DB_NAME = "pushapi";
 const kPUSHWSDB_DB_VERSION = 5; // Change this if the IndexedDB format changes
 const kPUSHWSDB_STORE_NAME = "pushapi";
 
-const kUDP_WAKEUP_WS_STATUS_CODE = 4774;  // WebSocket Close status code sent
-                                          // by server to signal that it can
-                                          // wake client up using UDP.
+// WebSocket close code sent by the server to indicate that the client should
+// not automatically reconnect.
+const kBACKOFF_WS_STATUS_CODE = 4774;
 
 // Maps ack statuses, unsubscribe reasons, and delivery error reasons to codes
 // included in request payloads.
 const kACK_STATUS_TO_CODE = {
   [Ci.nsIPushErrorReporter.ACK_DELIVERED]: 100,
   [Ci.nsIPushErrorReporter.ACK_DECRYPTION_ERROR]: 101,
   [Ci.nsIPushErrorReporter.ACK_NOT_DELIVERED]: 102,
 };
@@ -288,57 +281,22 @@ this.PushServiceWebSocket = {
   _requestTimeoutTimer: null,
   _retryFailCount: 0,
 
   /**
    * According to the WS spec, servers should immediately close the underlying
    * TCP connection after they close a WebSocket. This causes wsOnStop to be
    * called with error NS_BASE_STREAM_CLOSED. Since the client has to keep the
    * WebSocket up, it should try to reconnect. But if the server closes the
-   * WebSocket because it will wake up the client via UDP, then the client
-   * shouldn't re-establish the connection. If the server says that it will
-   * wake up the client over UDP, this is set to true in wsOnServerClose. It is
+   * WebSocket because it wants the client to back off, then the client
+   * shouldn't re-establish the connection. If the server sends the backoff
+   * close code, this field will be set to true in wsOnServerClose. It is
    * checked in wsOnStop.
    */
-  _willBeWokenUpByUDP: false,
-
-  /**
-   * Holds if the adaptive ping is enabled. This is read on init().
-   * If adaptive ping is enabled, a new ping is calculed each time we receive
-   * a pong message, trying to maximize network resources while minimizing
-   * cellular signalling storms.
-   */
-  _adaptiveEnabled: false,
-
-  /**
-   * This saves a flag about if we need to recalculate a new ping, based on:
-   *   1) the gap between the maximum working ping and the first ping that
-   *      gives an error (timeout) OR
-   *   2) we have reached the pref of the maximum value we allow for a ping
-   *      (dom.push.adaptive.upperLimit)
-   */
-  _recalculatePing: true,
-
-  /**
-   * This map holds a (pingInterval, triedTimes) of each pingInterval tried.
-   * It is used to check if the pingInterval has been tested enough to know that
-   * is incorrect and is above the limit the network allow us to keep the
-   * connection open.
-   */
-  _pingIntervalRetryTimes: {},
-
-  /**
-   * Holds the lastGoodPingInterval for our current connection.
-   */
-  _lastGoodPingInterval: 0,
-
-  /**
-   * Maximum ping interval that we can reach.
-   */
-  _upperLimit: 0,
+  _skipReconnect: false,
 
   /** Indicates whether the server supports Web Push-style message delivery. */
   _dataEnabled: false,
 
   /**
    * The last time the client sent a ping to the server. If non-zero, keeps the
    * request timeout timer active. Reset to zero when the server responds with
    * a pong or pending messages.
@@ -377,45 +335,31 @@ this.PushServiceWebSocket = {
 
     // Override the default WebSocket factory function. The returned object
     // must be null or satisfy the nsIWebSocketChannel interface. Used by
     // the tests to provide a mock WebSocket implementation.
     if (options.makeWebSocket) {
       this._makeWebSocket = options.makeWebSocket;
     }
 
-    // Override the default UDP socket factory function. The returned object
-    // must be null or satisfy the nsIUDPSocket interface. Used by the
-    // UDP tests.
-    if (options.makeUDPSocket) {
-      this._makeUDPSocket = options.makeUDPSocket;
-    }
-
-    this._networkInfo = options.networkInfo;
-    if (!this._networkInfo) {
-      this._networkInfo = PushNetworkInfo;
-    }
-
     this._requestTimeout = prefs.get("requestTimeout");
-    this._adaptiveEnabled = prefs.get('adaptive.enabled');
-    this._upperLimit = prefs.get('adaptive.upperLimit');
 
     return Promise.resolve();
   },
 
   _reconnect: function () {
     console.debug("reconnect()");
     this._shutdownWS(false);
     this._startBackoffTimer();
   },
 
   _shutdownWS: function(shouldCancelPending = true) {
     console.debug("shutdownWS()");
     this._currentState = STATE_SHUT_DOWN;
-    this._willBeWokenUpByUDP = false;
+    this._skipReconnect = false;
 
     prefs.ignore("userAgentID", this);
 
     if (this._wsListener) {
       this._wsListener._pushService = null;
     }
     try {
         this._ws.close(0, null);
@@ -434,21 +378,16 @@ this.PushServiceWebSocket = {
 
     if (this._notifyRequestQueue) {
       this._notifyRequestQueue();
       this._notifyRequestQueue = null;
     }
   },
 
   uninit: function() {
-    if (this._udpServer) {
-      this._udpServer.close();
-      this._udpServer = null;
-    }
-
     // All pending requests (ideally none) are dropped at this point. We
     // shouldn't have any applications performing registration/unregistration
     // or receiving notifications.
     this._shutdownWS();
 
     if (this._backoffTimer) {
       this._backoffTimer.cancel();
     }
@@ -457,33 +396,29 @@ this.PushServiceWebSocket = {
     }
 
     this._mainPushService = null;
 
     this._dataEnabled = false;
   },
 
   /**
-   * How retries work:  The goal is to ensure websocket is always up on
-   * networks not supporting UDP. So the websocket should only be shutdown if
-   * onServerClose indicates UDP wakeup.  If WS is closed due to socket error,
+   * How retries work: If the WS is closed due to a socket error,
    * _startBackoffTimer() is called. The retry timer is started and when
    * it times out, beginWSSetup() is called again.
    *
    * If we are in the middle of a timeout (i.e. waiting), but
    * a register/unregister is called, we don't want to wait around anymore.
    * _sendRequest will automatically call beginWSSetup(), which will cancel the
    * timer. In addition since the state will have changed, even if a pending
    * timer event comes in (because the timer fired the event before it was
    * cancelled), so the connection won't be reset.
    */
   _startBackoffTimer() {
     console.debug("startBackoffTimer()");
-    //Calculate new ping interval
-    this._calculateAdaptivePing(true /* wsWentDown */);
 
     // Calculate new timeout, but cap it to pingInterval.
     let retryTimeout = prefs.get("retryBaseInterval") *
                        Math.pow(2, this._retryFailCount);
     retryTimeout = Math.min(retryTimeout, prefs.get("pingInterval"));
 
     this._retryFailCount++;
 
@@ -524,166 +459,16 @@ this.PushServiceWebSocket = {
     if (!this._pingTimer) {
       this._pingTimer = Cc["@mozilla.org/timer;1"]
                           .createInstance(Ci.nsITimer);
     }
     this._pingTimer.init(this, prefs.get("pingInterval"),
                          Ci.nsITimer.TYPE_ONE_SHOT);
   },
 
-  /**
-   * We need to calculate a new ping based on:
-   *  1) Latest good ping
-   *  2) A safe gap between 1) and the calculated new ping (which is
-   *  by default, 1 minute)
-   *
-   * This is for 3G networks, whose connections keepalives differ broadly,
-   * for example:
-   *  1) Movistar Spain: 29 minutes
-   *  2) VIVO Brazil: 5 minutes
-   *  3) Movistar Colombia: XXX minutes
-   *
-   * So a fixed ping is not good for us for two reasons:
-   *  1) We might lose the connection, so we need to reconnect again (wasting
-   *  resources)
-   *  2) We use a lot of network signaling just for pinging.
-   *
-   * This algorithm tries to search the best value between a disconnection and a
-   * valid ping, to ensure better battery life and network resources usage.
-   *
-   * The value is saved in dom.push.pingInterval
-   * @param wsWentDown [Boolean] if the WebSocket was closed or it is still
-   * alive
-   *
-   */
-  _calculateAdaptivePing: function(wsWentDown) {
-    console.debug("_calculateAdaptivePing()");
-    if (!this._adaptiveEnabled) {
-      console.debug("calculateAdaptivePing: Adaptive ping is disabled");
-      return;
-    }
-
-    if (this._retryFailCount > 0) {
-      console.warn("calculateAdaptivePing: Push has failed to connect to the",
-        "Push Server", this._retryFailCount, "times. Do not calculate a new",
-        "pingInterval now");
-      return;
-    }
-
-    if (!this._recalculatePing && !wsWentDown) {
-      console.debug("calculateAdaptivePing: We do not need to recalculate the",
-        "ping now, based on previous data");
-      return;
-    }
-
-    // Save actual state of the network
-    let ns = this._networkInfo.getNetworkInformation();
-
-    if (ns.ip) {
-      // mobile
-      console.debug("calculateAdaptivePing: mobile");
-      let oldNetwork = prefs.get('adaptive.mobile');
-      let newNetwork = 'mobile-' + ns.mcc + '-' + ns.mnc;
-
-      // Mobile networks differ, reset all intervals and pings
-      if (oldNetwork !== newNetwork) {
-        // Network differ, reset all values
-        console.debug("calculateAdaptivePing: Mobile networks differ. Old",
-          "network is", oldNetwork, "and new is", newNetwork);
-        prefs.set('adaptive.mobile', newNetwork);
-        //We reset the upper bound member
-        this._recalculatePing = true;
-        this._pingIntervalRetryTimes = {};
-
-        // Put default values
-        let defaultPing = prefs.get('pingInterval.default');
-        prefs.set('pingInterval', defaultPing);
-        this._lastGoodPingInterval = defaultPing;
-
-      } else {
-        // Mobile network is the same, let's just update things
-        prefs.set('pingInterval', prefs.get('pingInterval.mobile'));
-        this._lastGoodPingInterval = prefs.get('adaptive.lastGoodPingInterval.mobile');
-      }
-
-    } else {
-      // wifi
-      console.debug("calculateAdaptivePing: wifi");
-      prefs.set('pingInterval', prefs.get('pingInterval.wifi'));
-      this._lastGoodPingInterval = prefs.get('adaptive.lastGoodPingInterval.wifi');
-    }
-
-    let nextPingInterval;
-    let lastTriedPingInterval = prefs.get('pingInterval');
-
-    if (wsWentDown) {
-      console.debug("calculateAdaptivePing: The WebSocket was disconnected.",
-        "Calculating next ping");
-
-      // If we have not tried this pingInterval yet, initialize
-      this._pingIntervalRetryTimes[lastTriedPingInterval] =
-           (this._pingIntervalRetryTimes[lastTriedPingInterval] || 0) + 1;
-
-       // Try the pingInterval at least 3 times, just to be sure that the
-       // calculated interval is not valid.
-       if (this._pingIntervalRetryTimes[lastTriedPingInterval] < 2) {
-         console.debug("calculateAdaptivePing: pingInterval=",
-          lastTriedPingInterval, "tried only",
-          this._pingIntervalRetryTimes[lastTriedPingInterval], "times");
-         return;
-       }
-
-       // Latest ping was invalid, we need to lower the limit to limit / 2
-       nextPingInterval = Math.floor(lastTriedPingInterval / 2);
-
-      // If the new ping interval is close to the last good one, we are near
-      // optimum, so stop calculating.
-      if (nextPingInterval - this._lastGoodPingInterval <
-          prefs.get('adaptive.gap')) {
-        console.debug("calculateAdaptivePing: We have reached the gap, we",
-          "have finished the calculation. nextPingInterval=", nextPingInterval,
-          "lastGoodPing=", this._lastGoodPingInterval);
-        nextPingInterval = this._lastGoodPingInterval;
-        this._recalculatePing = false;
-      } else {
-        console.debug("calculateAdaptivePing: We need to calculate next time");
-        this._recalculatePing = true;
-      }
-
-    } else {
-      console.debug("calculateAdaptivePing: The WebSocket is still up");
-      this._lastGoodPingInterval = lastTriedPingInterval;
-      nextPingInterval = Math.floor(lastTriedPingInterval * 1.5);
-    }
-
-    // Check if we have reached the upper limit
-    if (this._upperLimit < nextPingInterval) {
-      console.debug("calculateAdaptivePing: Next ping will be bigger than the",
-        "configured upper limit, capping interval");
-      this._recalculatePing = false;
-      this._lastGoodPingInterval = lastTriedPingInterval;
-      nextPingInterval = lastTriedPingInterval;
-    }
-
-    console.debug("calculateAdaptivePing: Setting the pingInterval to",
-      nextPingInterval);
-    prefs.set('pingInterval', nextPingInterval);
-
-    //Save values for our current network
-    if (ns.ip) {
-      prefs.set('pingInterval.mobile', nextPingInterval);
-      prefs.set('adaptive.lastGoodPingInterval.mobile',
-                this._lastGoodPingInterval);
-    } else {
-      prefs.set('pingInterval.wifi', nextPingInterval);
-      prefs.set('adaptive.lastGoodPingInterval.wifi',
-                this._lastGoodPingInterval);
-    }
-  },
-
   _makeWebSocket: function(uri) {
     if (!prefs.get("connection.enabled")) {
       console.warn("makeWebSocket: connection.enabled is not set to true.",
         "Aborting.");
       return null;
     }
     if (Services.io.offline) {
       console.warn("makeWebSocket: Network is offline.");
@@ -1189,53 +974,33 @@ this.PushServiceWebSocket = {
       messageType: "hello",
       use_webpush: true,
     };
 
     if (this._UAID) {
       data.uaid = this._UAID;
     }
 
-    this._networkInfo.getNetworkState((networkState) => {
-      if (networkState.ip) {
-        // Opening an available UDP port.
-        this._listenForUDPWakeup();
-
-        // Host-port is apparently a thing.
-        data.wakeup_hostport = {
-          ip: networkState.ip,
-          port: this._udpServer && this._udpServer.port
-        };
-
-        data.mobilenetwork = {
-          mcc: networkState.mcc,
-          mnc: networkState.mnc,
-          netid: networkState.netid
-        };
-      }
-
-      this._wsSendMessage(data);
-      this._currentState = STATE_WAITING_FOR_HELLO;
-    });
+    this._wsSendMessage(data);
+    this._currentState = STATE_WAITING_FOR_HELLO;
   },
 
   /**
    * This statusCode is not the websocket protocol status code, but the TCP
    * connection close status code.
    *
    * If we do not explicitly call ws.close() then statusCode is always
    * NS_BASE_STREAM_CLOSED, even on a successful close.
    */
   _wsOnStop: function(context, statusCode) {
     console.debug("wsOnStop()");
     this._releaseWakeLock();
 
-    if (statusCode != Cr.NS_OK &&
-        !(statusCode == Cr.NS_BASE_STREAM_CLOSED && this._willBeWokenUpByUDP)) {
-      console.debug("wsOnStop: Socket error", statusCode);
+    if (statusCode != Cr.NS_OK && !this._skipReconnect) {
+      console.debug("wsOnStop: Reconnecting after socket error", statusCode);
       this._reconnect();
       return;
     }
 
     this._shutdownWS();
   },
 
   _wsOnMessageAvailable: function(context, message) {
@@ -1250,25 +1015,23 @@ this.PushServiceWebSocket = {
     } catch(e) {
       console.warn("wsOnMessageAvailable: Invalid JSON", message, e);
       return;
     }
 
     // If we receive a message, we know the connection succeeded. Reset the
     // connection attempt and ping interval counters.
     this._retryFailCount = 0;
-    this._pingIntervalRetryTimes = {};
 
     let doNotHandle = false;
     if ((message === '{}') ||
         (reply.messageType === undefined) ||
         (reply.messageType === "ping") ||
         (typeof reply.messageType != "string")) {
       console.debug("wsOnMessageAvailable: Pong received");
-      this._calculateAdaptivePing(false);
       doNotHandle = true;
     }
 
     // Reset the ping timer.  Note: This path is executed at every step of the
     // handshake, so this timer does not need to be set explicitly at startup.
     this._startPingTimer();
 
     // If it is a ping, do not handle the message.
@@ -1303,220 +1066,38 @@ this.PushServiceWebSocket = {
   },
 
   /**
    * The websocket should never be closed. Since we don't call ws.close(),
    * _wsOnStop() receives error code NS_BASE_STREAM_CLOSED (see comment in that
    * function), which calls reconnect and re-establishes the WebSocket
    * connection.
    *
-   * If the server said it'll use UDP for wakeup, we set _willBeWokenUpByUDP
-   * and stop reconnecting in _wsOnStop().
+   * If the server requested that we back off, we won't reconnect until the
+   * next network state change event, or until we need to send a new register
+   * request.
    */
   _wsOnServerClose: function(context, aStatusCode, aReason) {
     console.debug("wsOnServerClose()", aStatusCode, aReason);
 
-    // Switch over to UDP.
-    if (aStatusCode == kUDP_WAKEUP_WS_STATUS_CODE) {
-      console.debug("wsOnServerClose: Server closed with promise to wake up");
-      this._willBeWokenUpByUDP = true;
-      // TODO: there should be no pending requests
+    if (aStatusCode == kBACKOFF_WS_STATUS_CODE) {
+      console.debug("wsOnServerClose: Skipping automatic reconnect");
+      this._skipReconnect = true;
     }
   },
 
   /**
    * Rejects all pending register requests with errors.
    */
   _cancelRegisterRequests: function() {
     for (let request of this._registerRequests.values()) {
       request.reject(new Error("Register request aborted"));
     }
     this._registerRequests.clear();
   },
-
-  _makeUDPSocket: function() {
-    return Cc["@mozilla.org/network/udp-socket;1"]
-             .createInstance(Ci.nsIUDPSocket);
-  },
-
-  /**
-   * This method should be called only if the device is on a mobile network!
-   */
-  _listenForUDPWakeup: function() {
-    console.debug("listenForUDPWakeup()");
-
-    if (this._udpServer) {
-      console.warn("listenForUDPWakeup: UDP Server already running");
-      return;
-    }
-
-    if (!prefs.get("udp.wakeupEnabled")) {
-      console.debug("listenForUDPWakeup: UDP support disabled");
-      return;
-    }
-
-    let socket = this._makeUDPSocket();
-    if (!socket) {
-      return;
-    }
-    this._udpServer = socket.QueryInterface(Ci.nsIUDPSocket);
-    this._udpServer.init(-1, false, Services.scriptSecurityManager.getSystemPrincipal());
-    this._udpServer.asyncListen(this);
-    console.debug("listenForUDPWakeup: Listening on", this._udpServer.port);
-
-    return this._udpServer.port;
-  },
-
-  /**
-   * Called by UDP Server Socket. As soon as a ping is received via UDP,
-   * reconnect the WebSocket and get the actual data.
-   */
-  onPacketReceived: function(aServ, aMessage) {
-    console.debug("onPacketReceived: Recv UDP datagram on port",
-      this._udpServer.port);
-    this._beginWSSetup();
-  },
-
-  /**
-   * Called by UDP Server Socket if the socket was closed for some reason.
-   *
-   * If this happens, we reconnect the WebSocket to not miss out on
-   * notifications.
-   */
-  onStopListening: function(aServ, aStatus) {
-    console.debug("onStopListening: UDP Server socket was shutdown. Status",
-      aStatus);
-    this._udpServer = undefined;
-    this._beginWSSetup();
-  },
-};
-
-var PushNetworkInfo = {
-  /**
-   * Returns information about MCC-MNC and the IP of the current connection.
-   */
-  getNetworkInformation: function() {
-    console.debug("PushNetworkInfo: getNetworkInformation()");
-
-    try {
-      if (!prefs.get("udp.wakeupEnabled")) {
-        console.debug("getNetworkInformation: UDP support disabled, we do not",
-          "send any carrier info");
-        throw new Error("UDP disabled");
-      }
-
-      let nm = Cc["@mozilla.org/network/manager;1"]
-                 .getService(Ci.nsINetworkManager);
-      if (nm.activeNetworkInfo &&
-          nm.activeNetworkInfo.type == Ci.nsINetworkInfo.NETWORK_TYPE_MOBILE) {
-        let iccService = Cc["@mozilla.org/icc/iccservice;1"]
-                           .getService(Ci.nsIIccService);
-        // TODO: Bug 927721 - PushService for multi-sim
-        // In Multi-sim, there is more than one client in iccService. Each
-        // client represents a icc handle. To maintain backward compatibility
-        // with single sim, we always use client 0 for now. Adding support
-        // for multiple sim will be addressed in bug 927721, if needed.
-        let clientId = 0;
-        let icc = iccService.getIccByServiceId(clientId);
-        let iccInfo = icc && icc.iccInfo;
-        if (iccInfo) {
-          console.debug("getNetworkInformation: Running on mobile data");
-
-          let ips = {};
-          let prefixLengths = {};
-          nm.activeNetworkInfo.getAddresses(ips, prefixLengths);
-
-          return {
-            mcc: iccInfo.mcc,
-            mnc: iccInfo.mnc,
-            ip:  ips.value[0]
-          };
-        }
-      }
-    } catch (e) {
-      console.error("getNetworkInformation: Error recovering mobile network",
-        "information", e);
-    }
-
-    console.debug("getNetworkInformation: Running on wifi");
-    return {
-      mcc: 0,
-      mnc: 0,
-      ip: undefined
-    };
-  },
-
-  /**
-   * Get mobile network information to decide if the client is capable of being
-   * woken up by UDP (which currently just means having an mcc and mnc along
-   * with an IP, and optionally a netid).
-   */
-  getNetworkState: function(callback) {
-    console.debug("PushNetworkInfo: getNetworkState()");
-
-    if (typeof callback !== 'function') {
-      throw new Error("No callback method. Aborting push agent !");
-    }
-
-    var networkInfo = this.getNetworkInformation();
-
-    if (networkInfo.ip) {
-      this._getMobileNetworkId(networkInfo, function(netid) {
-        console.debug("getNetworkState: Recovered netID", netid);
-        callback({
-          mcc: networkInfo.mcc,
-          mnc: networkInfo.mnc,
-          ip:  networkInfo.ip,
-          netid: netid
-        });
-      });
-    } else {
-      callback(networkInfo);
-    }
-  },
-
-  /*
-   * Get the mobile network ID (netid)
-   *
-   * @param networkInfo
-   *        Network information object { mcc, mnc, ip, port }
-   * @param callback
-   *        Callback function to invoke with the netid or null if not found
-   */
-  _getMobileNetworkId: function(networkInfo, callback) {
-    console.debug("PushNetworkInfo: getMobileNetworkId()");
-    if (typeof callback !== 'function') {
-      return;
-    }
-
-    function queryDNSForDomain(domain) {
-      console.debug("queryDNSForDomain: Querying DNS for", domain);
-      let netIDDNSListener = {
-        onLookupComplete: function(aRequest, aRecord, aStatus) {
-          if (aRecord) {
-            let netid = aRecord.getNextAddrAsString();
-            console.debug("queryDNSForDomain: NetID found", netid);
-            callback(netid);
-          } else {
-            console.debug("queryDNSForDomain: NetID not found");
-            callback(null);
-          }
-        }
-      };
-      gDNSService.asyncResolve(domain, 0, netIDDNSListener,
-        threadManager.currentThread);
-      return [];
-    }
-
-    console.debug("getMobileNetworkId: Getting mobile network ID");
-
-    let netidAddress = "wakeup.mnc" + ("00" + networkInfo.mnc).slice(-3) +
-      ".mcc" + ("00" + networkInfo.mcc).slice(-3) + ".3gppnetwork.org";
-    queryDNSForDomain(netidAddress, callback);
-  }
 };
 
 function PushRecordWebSocket(record) {
   PushRecord.call(this, record);
   this.channelID = record.channelID;
   this.version = record.version;
 }
 
--- a/dom/push/PushSubscription.cpp
+++ b/dom/push/PushSubscription.cpp
@@ -133,17 +133,17 @@ private:
   {
   }
 
   RefPtr<PromiseWorkerProxy> mProxy;
 };
 
 NS_IMPL_ISUPPORTS(WorkerUnsubscribeResultCallback, nsIUnsubscribeResultCallback)
 
-class UnsubscribeRunnable final : public nsRunnable
+class UnsubscribeRunnable final : public Runnable
 {
 public:
   UnsubscribeRunnable(PromiseWorkerProxy* aProxy,
                       const nsAString& aScope)
     : mProxy(aProxy)
     , mScope(aScope)
   {
     MOZ_ASSERT(aProxy);
@@ -336,32 +336,30 @@ PushSubscription::GetKey(JSContext* aCx,
 }
 
 void
 PushSubscription::ToJSON(PushSubscriptionJSON& aJSON, ErrorResult& aRv)
 {
   aJSON.mEndpoint.Construct();
   aJSON.mEndpoint.Value() = mEndpoint;
 
-  Base64URLEncodeOptions encodeOptions;
-  encodeOptions.mPad = false;
-
   aJSON.mKeys.mP256dh.Construct();
   nsresult rv = Base64URLEncode(mRawP256dhKey.Length(),
                                 mRawP256dhKey.Elements(),
-                                encodeOptions,
+                                Base64URLEncodePaddingPolicy::Omit,
                                 aJSON.mKeys.mP256dh.Value());
   if (NS_WARN_IF(NS_FAILED(rv))) {
     aRv.Throw(rv);
     return;
   }
 
   aJSON.mKeys.mAuth.Construct();
   rv = Base64URLEncode(mAuthSecret.Length(), mAuthSecret.Elements(),
-                       encodeOptions, aJSON.mKeys.mAuth.Value());
+                       Base64URLEncodePaddingPolicy::Omit,
+                       aJSON.mKeys.mAuth.Value());
   if (NS_WARN_IF(NS_FAILED(rv))) {
     aRv.Throw(rv);
     return;
   }
 }
 
 already_AddRefed<PushSubscriptionOptions>
 PushSubscription::Options()
--- a/dom/push/test/mockpushserviceparent.js
+++ b/dom/push/test/mockpushserviceparent.js
@@ -56,43 +56,26 @@ MockWebSocketParent.prototype = {
   },
 
   serverSendMsg(msg) {
     waterfall(() => this._listener.onMessageAvailable(this._context, msg),
               () => this._listener.onAcknowledge(this._context, 0));
   },
 };
 
-function MockNetworkInfo() {}
-
-MockNetworkInfo.prototype = {
-  getNetworkInformation() {
-    return {mcc: '', mnc: '', ip: ''};
-  },
-
-  getNetworkState(callback) {
-    callback({mcc: '', mnc: '', ip: '', netid: ''});
-  },
-
-  getNetworkStateChangeEventName() {
-    return 'network:offline-status-changed';
-  }
-};
-
 var pushService = Cc["@mozilla.org/push/Service;1"].
                   getService(Ci.nsIPushService).
                   wrappedJSObject;
 
 var mockSocket;
 var serverMsgs = [];
 
 addMessageListener("socket-setup", function () {
   pushService.replaceServiceBackend({
     serverURI: "wss://push.example.org/",
-    networkInfo: new MockNetworkInfo(),
     makeWebSocket(uri) {
       mockSocket = new MockWebSocketParent(uri);
       while (serverMsgs.length > 0) {
         let msg = serverMsgs.shift();
         mockSocket.serverSendMsg(msg);
       }
       return mockSocket;
     }
--- a/dom/push/test/xpcshell/head.js
+++ b/dom/push/test/xpcshell/head.js
@@ -135,34 +135,21 @@ function makeStub(target, stubs) {
  */
 function setPrefs(prefs = {}) {
   let defaultPrefs = Object.assign({
     loglevel: 'all',
     serverURL: 'wss://push.example.org',
     'connection.enabled': true,
     userAgentID: '',
     enabled: true,
-    // Disable adaptive pings and UDP wake-up by default; these are
-    // tested separately.
-    'adaptive.enabled': false,
-    'udp.wakeupEnabled': false,
-    // Defaults taken from /b2g/app/b2g.js.
+    // Defaults taken from /modules/libpref/init/all.js.
     requestTimeout: 10000,
     retryBaseInterval: 5000,
     pingInterval: 30 * 60 * 1000,
-    'pingInterval.default': 3 * 60 * 1000,
-    'pingInterval.mobile': 3 * 60 * 1000,
-    'pingInterval.wifi': 3 * 60 * 1000,
-    'adaptive.lastGoodPingInterval': 3 * 60 * 1000,
-    'adaptive.lastGoodPingInterval.mobile': 3 * 60 * 1000,
-    'adaptive.lastGoodPingInterval.wifi': 3 * 60 * 1000,
-    'adaptive.gap': 60000,
-    'adaptive.upperLimit': 29 * 60 * 1000,
     // Misc. defaults.
-    'adaptive.mobile': '',
     'http2.maxRetries': 2,
     'http2.retryInterval': 500,
     'http2.reset_retry_count_after_ms': 60000,
     maxQuotaPerSubscription: 16,
     quotaUpdateDelay: 3000,
     'testing.notifyWorkers': false,
     'testing.notifyAllObservers': true,
   }, prefs);
@@ -303,18 +290,17 @@ MockWebSocket.prototype = {
     waterfall(
       () => this._listener.onMessageAvailable(this._context, msg),
       () => this._listener.onAcknowledge(this._context, 0)
     );
   },
 
   /**
    * Closes the server end of the connection, calling onServerClose()
-   * followed by onStop(). Used to test abrupt connection termination
-   * and UDP wake-up.
+   * followed by onStop(). Used to test abrupt connection termination.
    *
    * @param {Number} [statusCode] The WebSocket connection close code.
    * @param {String} [reason] The connection close reason.
    */
   serverClose(statusCode, reason = '') {
     if (!isFinite(statusCode)) {
       statusCode = WEBSOCKET_CLOSE_GOING_AWAY;
     }
@@ -324,68 +310,16 @@ MockWebSocket.prototype = {
     );
   },
 
   serverInterrupt(result = Cr.NS_ERROR_NET_RESET) {
     waterfall(() => this._listener.onStop(this._context, result));
   },
 };
 
-/**
- * Creates an object that exposes the same interface as NetworkInfo, used
- * to simulate network status changes on Desktop. All methods returns empty
- * carrier data.
- */
-function MockDesktopNetworkInfo() {}
-
-MockDesktopNetworkInfo.prototype = {
-  getNetworkInformation() {
-    return {mcc: '', mnc: '', ip: ''};
-  },
-
-  getNetworkState(callback) {
-    callback({mcc: '', mnc: '', ip: '', netid: ''});
-  },