Bug 1423241 - Ignore runnables for main thread after next stream state update, after entering shutdown. r=padenot
authorAndreas Pehrson <apehrson@mozilla.com>
Fri, 23 Nov 2018 15:02:42 +0000
changeset 504280 d4767402cbb352274a930b0c800626c5e34b49ae
parent 504279 3c5df9713725b2dd36b4af9eed890d70ed073d78
child 504281 47958cf495da3a425773827f276ee8161d137cc6
push id10290
push userffxbld-merge
push dateMon, 03 Dec 2018 16:23:23 +0000
treeherdermozilla-beta@700bed2445e6 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerspadenot
bugs1423241
milestone65.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1423241 - Ignore runnables for main thread after next stream state update, after entering shutdown. r=padenot They may hang on to references causing leaks. Differential Revision: https://phabricator.services.mozilla.com/D12281
dom/media/MediaStreamGraph.cpp
dom/media/MediaStreamGraph.h
dom/media/MediaStreamGraphImpl.h
--- a/dom/media/MediaStreamGraph.cpp
+++ b/dom/media/MediaStreamGraph.cpp
@@ -1557,16 +1557,19 @@ class MediaStreamGraphShutDownRunnable :
       if (SourceMediaStream* source = stream->AsSourceStream()) {
         // Finishing a SourceStream prevents new data from being appended.
         source->FinishOnGraphThread();
       }
       stream->GetStreamTracks().Clear();
       stream->RemoveAllListenersImpl();
     }
 
+    MOZ_ASSERT(mGraph->mUpdateRunnables.IsEmpty());
+    mGraph->mPendingUpdateRunnables.Clear();
+
     mGraph->mForceShutdownTicket = nullptr;
 
     // We can't block past the final LIFECYCLE_WAITING_FOR_STREAM_DESTRUCTION
     // stage, since completion of that stage requires all streams to be freed,
     // which requires shutdown to proceed.
 
     if (mGraph->IsEmpty()) {
       // mGraph is no longer needed, so delete it.
@@ -3999,17 +4002,18 @@ already_AddRefed<MediaInputPort> MediaSt
     }
   }
   return nullptr;
 }
 
 void MediaStreamGraph::DispatchToMainThreadAfterStreamStateUpdate(
     already_AddRefed<nsIRunnable> aRunnable) {
   AssertOnGraphThreadOrNotRunning();
-  *mPendingUpdateRunnables.AppendElement() =
+  *static_cast<MediaStreamGraphImpl*>(this)
+       ->mPendingUpdateRunnables.AppendElement() =
       AbstractMainThread()->CreateDirectTaskDrainer(std::move(aRunnable));
 }
 
 Watchable<mozilla::GraphTime>& MediaStreamGraphImpl::CurrentTime() {
   MOZ_ASSERT(NS_IsMainThread());
   return mMainThreadGraphTime;
 }
 
--- a/dom/media/MediaStreamGraph.h
+++ b/dom/media/MediaStreamGraph.h
@@ -1319,18 +1319,21 @@ class MediaStreamGraph {
 
   /**
    * Media graph thread only.
    * Dispatches a runnable that will run on the main thread after all
    * main-thread stream state has been next updated.
    *
    * Should only be called during MediaStreamListener callbacks or during
    * ProcessedMediaStream::ProcessInput().
+   *
+   * Note that if called during shutdown the runnable will be ignored and
+   * released on main thread.
    */
-  virtual void DispatchToMainThreadAfterStreamStateUpdate(
+  void DispatchToMainThreadAfterStreamStateUpdate(
       already_AddRefed<nsIRunnable> aRunnable);
 
   /**
    * Returns graph sample rate in Hz.
    */
   TrackRate GraphRate() const { return mSampleRate; }
 
   void RegisterCaptureStreamForWindow(uint64_t aWindowId,
@@ -1355,19 +1358,16 @@ class MediaStreamGraph {
   }
   virtual ~MediaStreamGraph() { MOZ_COUNT_DTOR(MediaStreamGraph); }
 
   // Intended only for assertions, either on graph thread or not running (in
   // which case we must be on the main thread).
   bool OnGraphThreadOrNotRunning() const;
   bool OnGraphThread() const;
 
-  // Media graph thread only
-  nsTArray<nsCOMPtr<nsIRunnable>> mPendingUpdateRunnables;
-
   /**
    * Sample rate at which this graph runs. For real time graphs, this is
    * the rate of the audio mixer. For offline graphs, this is the rate specified
    * at construction.
    */
   TrackRate mSampleRate;
 };
 
--- a/dom/media/MediaStreamGraphImpl.h
+++ b/dom/media/MediaStreamGraphImpl.h
@@ -647,16 +647,21 @@ class MediaStreamGraphImpl : public Medi
   /**
    * Date of the last time we updated the main thread with the graph state.
    */
   TimeStamp mLastMainThreadUpdate;
   /**
    * Number of active MediaInputPorts
    */
   int32_t mPortCount;
+  /**
+   * Runnables to run after the next update to main thread state, but that are
+   * still waiting for the next iteration to finish.
+   */
+  nsTArray<nsCOMPtr<nsIRunnable>> mPendingUpdateRunnables;
 
   /**
    * Devices to use for cubeb input & output, or nullptr for default device.
    * A MediaStreamGraph always has an output (even if silent).
    * If `mInputDeviceUsers.Count() != 0`, this MediaStreamGraph wants audio
    * input.
    *
    * In any case, the number of channels to use can be queried (on the graph