Bug 1343787 - Allow MediaShutdownManager::Register() to fail. r=gerald, a=jcristau
authorJW Wang <jwwang@mozilla.com>
Mon, 06 Mar 2017 10:36:12 +0800
changeset 355433 28287b7f0938f0d469cd10bb4a91151d10c7ec0d
parent 355432 10285b4a6b717bdd02644d87bbfda7fba45b37c4
child 355434 d2d79cb3dc239f9413f3690bcea2df9598ea4735
push id6974
push usercbook@mozilla.com
push dateFri, 24 Mar 2017 14:37:32 +0000
treeherdermozilla-esr52@28287b7f0938 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersgerald, jcristau
bugs1343787
milestone52.0.2
Bug 1343787 - Allow MediaShutdownManager::Register() to fail. r=gerald, a=jcristau Also move the Register() calls to Load().
dom/media/MediaDecoder.cpp
dom/media/MediaShutdownManager.cpp
dom/media/MediaShutdownManager.h
dom/media/mediasource/MediaSourceDecoder.cpp
dom/media/moz.build
--- a/dom/media/MediaDecoder.cpp
+++ b/dom/media/MediaDecoder.cpp
@@ -445,17 +445,16 @@ MediaDecoder::MediaDecoder(MediaDecoderO
   mWatchManager.Watch(mLogicallySeeking, &MediaDecoder::UpdateLogicalPosition);
 
   // mIgnoreProgressData
   mWatchManager.Watch(mLogicallySeeking, &MediaDecoder::SeekingChanged);
 
   mWatchManager.Watch(mIsAudioDataAudible, &MediaDecoder::NotifyAudibleStateChanged);
 
   MediaShutdownManager::InitStatics();
-  MediaShutdownManager::Instance().Register(this);
 }
 
 #undef INIT_MIRROR
 #undef INIT_CANONICAL
 
 void
 MediaDecoder::Shutdown()
 {
@@ -612,17 +611,22 @@ MediaDecoder::OpenResource(nsIStreamList
 }
 
 nsresult
 MediaDecoder::Load(nsIStreamListener** aStreamListener)
 {
   MOZ_ASSERT(NS_IsMainThread());
   MOZ_ASSERT(mResource, "Can't load without a MediaResource");
 
-  nsresult rv = OpenResource(aStreamListener);
+  nsresult rv = MediaShutdownManager::Instance().Register(this);
+  if (NS_WARN_IF(NS_FAILED(rv))) {
+    return rv;
+  }
+
+  rv = OpenResource(aStreamListener);
   NS_ENSURE_SUCCESS(rv, rv);
 
   SetStateMachine(CreateStateMachine());
   NS_ENSURE_TRUE(GetStateMachine(), NS_ERROR_FAILURE);
 
   return InitializeStateMachine();
 }
 
--- a/dom/media/MediaShutdownManager.cpp
+++ b/dom/media/MediaShutdownManager.cpp
@@ -95,34 +95,39 @@ MediaShutdownManager::RemoveBlocker()
   MOZ_ASSERT(mDecoders.Count() == 0);
   GetShutdownBarrier()->RemoveBlocker(this);
   // Clear our singleton reference. This will probably delete
   // this instance, so don't deref |this| clearing sInstance.
   sInstance = nullptr;
   DECODER_LOG(LogLevel::Debug, ("MediaShutdownManager::BlockShutdown() end."));
 }
 
-void
+nsresult
 MediaShutdownManager::Register(MediaDecoder* aDecoder)
 {
   MOZ_ASSERT(NS_IsMainThread());
-  MOZ_RELEASE_ASSERT(!mIsDoingXPCOMShutDown);
+  if (mIsDoingXPCOMShutDown) {
+    return NS_ERROR_ABORT;
+  }
   // Don't call Register() after you've Unregistered() all the decoders,
   // that's not going to work.
   MOZ_ASSERT(!mDecoders.Contains(aDecoder));
   mDecoders.PutEntry(aDecoder);
   MOZ_ASSERT(mDecoders.Contains(aDecoder));
   MOZ_ASSERT(mDecoders.Count() > 0);
+  return NS_OK;
 }
 
 void
 MediaShutdownManager::Unregister(MediaDecoder* aDecoder)
 {
   MOZ_ASSERT(NS_IsMainThread());
-  MOZ_ASSERT(mDecoders.Contains(aDecoder));
+  if (!mDecoders.Contains(aDecoder)) {
+    return;
+  }
   mDecoders.RemoveEntry(aDecoder);
   if (mIsDoingXPCOMShutDown && mDecoders.Count() == 0) {
     RemoveBlocker();
   }
 }
 
 NS_IMETHODIMP
 MediaShutdownManager::GetName(nsAString& aName)
--- a/dom/media/MediaShutdownManager.h
+++ b/dom/media/MediaShutdownManager.h
@@ -57,17 +57,17 @@ public:
   static void InitStatics();
 
   // The MediaShutdownManager is a singleton, access its instance with
   // this accessor.
   static MediaShutdownManager& Instance();
 
   // Notifies the MediaShutdownManager that it needs to track the shutdown
   // of this MediaDecoder.
-  void Register(MediaDecoder* aDecoder);
+  nsresult Register(MediaDecoder* aDecoder);
 
   // Notifies the MediaShutdownManager that a MediaDecoder that it was
   // tracking has shutdown, and it no longer needs to be shutdown in the
   // xpcom-shutdown listener.
   void Unregister(MediaDecoder* aDecoder);
 
 private:
 
--- a/dom/media/mediasource/MediaSourceDecoder.cpp
+++ b/dom/media/mediasource/MediaSourceDecoder.cpp
@@ -3,16 +3,17 @@
 /* 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 "MediaSourceDecoder.h"
 
 #include "mozilla/Logging.h"
 #include "mozilla/dom/HTMLMediaElement.h"
 #include "MediaDecoderStateMachine.h"
+#include "MediaShutdownManager.h"
 #include "MediaSource.h"
 #include "MediaSourceResource.h"
 #include "MediaSourceUtils.h"
 #include "VideoUtils.h"
 #include "MediaSourceDemuxer.h"
 #include "SourceBufferList.h"
 #include <algorithm>
 
@@ -49,23 +50,29 @@ MediaSourceDecoder::CreateStateMachine()
   return new MediaDecoderStateMachine(this, mReader);
 }
 
 nsresult
 MediaSourceDecoder::Load(nsIStreamListener**)
 {
   MOZ_ASSERT(NS_IsMainThread());
   MOZ_ASSERT(!GetStateMachine());
+
+  nsresult rv = MediaShutdownManager::Instance().Register(this);
+  if (NS_WARN_IF(NS_FAILED(rv))) {
+    return rv;
+  }
+
   SetStateMachine(CreateStateMachine());
   if (!GetStateMachine()) {
     NS_WARNING("Failed to create state machine!");
     return NS_ERROR_FAILURE;
   }
 
-  nsresult rv = GetStateMachine()->Init(this);
+  rv = GetStateMachine()->Init(this);
   NS_ENSURE_SUCCESS(rv, rv);
 
   SetStateMachineParameters();
   return NS_OK;
 }
 
 media::TimeIntervals
 MediaSourceDecoder::GetSeekable()
--- a/dom/media/moz.build
+++ b/dom/media/moz.build
@@ -115,16 +115,17 @@ EXPORTS += [
     'MediaMetadataManager.h',
     'MediaPrefs.h',
     'MediaQueue.h',
     'MediaRecorder.h',
     'MediaResource.h',
     'MediaResourceCallback.h',
     'MediaResult.h',
     'MediaSegment.h',
+    'MediaShutdownManager.h',
     'MediaStatistics.h',
     'MediaStreamGraph.h',
     'MediaStreamListener.h',
     'MediaStreamVideoSink.h',
     'MediaTimer.h',
     'MediaTrack.h',
     'MediaTrackList.h',
     'MP3Decoder.h',