Bug 973696 - fix CameraControl lifetime regressions in WebRTC, r=jesup
authorMike Habicher <mikeh@mozilla.com>
Wed, 19 Feb 2014 23:18:50 -0500
changeset 170000 01fa011daae62329a33c14279976d621fd7b8550
parent 169999 2164a17057a8ff7cc074f55b22d842b095003b54
child 170001 4ab6a5b763d8221dd2a189b106bba60b202fd6c2
push id270
push userpvanderbeken@mozilla.com
push dateThu, 06 Mar 2014 09:24:21 +0000
reviewersjesup
bugs973696
milestone30.0a1
Bug 973696 - fix CameraControl lifetime regressions in WebRTC, r=jesup
content/media/webrtc/MediaEngineWebRTC.h
content/media/webrtc/MediaEngineWebRTCVideo.cpp
--- a/content/media/webrtc/MediaEngineWebRTC.h
+++ b/content/media/webrtc/MediaEngineWebRTC.h
@@ -149,18 +149,23 @@ public:
                           TrackID aId,
                           StreamTime aDesiredTime,
                           TrackTicks &aLastEndTime);
 
   virtual bool IsFake() {
     return false;
   }
 
+#ifndef MOZ_B2G_CAMERA
   NS_DECL_THREADSAFE_ISUPPORTS
-#ifdef MOZ_B2G_CAMERA
+#else
+  // We are subclassed from CameraControlListener, which implements a
+  // threadsafe reference-count for us.
+  NS_DECL_ISUPPORTS_INHERITED
+
   void OnHardwareStateChange(HardwareState aState);
   void OnConfigurationChange(const CameraListenerConfiguration& aConfiguration);
   bool OnNewPreviewFrame(layers::Image* aImage, uint32_t aWidth, uint32_t aHeight);
   void OnError(CameraErrorContext aContext, const nsACString& aError);
   void OnTakePictureComplete(uint8_t* aData, uint32_t aLength, const nsAString& aMimeType);
 
   void AllocImpl();
   void DeallocImpl();
--- a/content/media/webrtc/MediaEngineWebRTCVideo.cpp
+++ b/content/media/webrtc/MediaEngineWebRTCVideo.cpp
@@ -20,17 +20,23 @@ extern PRLogModuleInfo* GetMediaManagerL
 #else
 #define LOG(msg)
 #define LOGFRAME(msg)
 #endif
 
 /**
  * Webrtc video source.
  */
+#ifndef MOZ_B2G_CAMERA
 NS_IMPL_ISUPPORTS1(MediaEngineWebRTCVideoSource, nsIRunnable)
+#else
+NS_IMPL_QUERY_INTERFACE1(MediaEngineWebRTCVideoSource, nsIRunnable)
+NS_IMPL_ADDREF_INHERITED(MediaEngineWebRTCVideoSource, CameraControlListener)
+NS_IMPL_RELEASE_INHERITED(MediaEngineWebRTCVideoSource, CameraControlListener)
+#endif
 
 // ViEExternalRenderer Callback.
 #ifndef MOZ_B2G_CAMERA
 int
 MediaEngineWebRTCVideoSource::FrameSizeChange(
    unsigned int w, unsigned int h, unsigned int streams)
 {
   mWidth = w;
@@ -490,16 +496,20 @@ MediaEngineWebRTCVideoSource::Shutdown()
 #ifdef MOZ_B2G_CAMERA
 
 // All these functions must be run on MainThread!
 void
 MediaEngineWebRTCVideoSource::AllocImpl() {
   MOZ_ASSERT(NS_IsMainThread());
 
   mCameraControl = ICameraControl::Create(mCaptureIndex, nullptr);
+
+  // Add this as a listener for CameraControl events. We don't need
+  // to explicitly remove this--destroying the CameraControl object
+  // in DeallocImpl() will do that for us.
   mCameraControl->AddListener(this);
 }
 
 void
 MediaEngineWebRTCVideoSource::DeallocImpl() {
   MOZ_ASSERT(NS_IsMainThread());
 
   mCameraControl->ReleaseHardware();
@@ -534,17 +544,16 @@ MediaEngineWebRTCVideoSource::SnapshotIm
 void
 MediaEngineWebRTCVideoSource::OnHardwareStateChange(HardwareState aState)
 {
   ReentrantMonitorAutoEnter sync(mCallbackMonitor);
   if (aState == CameraControlListener::kHardwareOpen) {
     mState = kAllocated;
   } else {
     mState = kReleased;
-    mCameraControl->RemoveListener(this);
   }
   mCallbackMonitor.Notify();
 }
 
 void
 MediaEngineWebRTCVideoSource::OnConfigurationChange(const CameraListenerConfiguration& aConfiguration)
 {
   ReentrantMonitorAutoEnter sync(mCallbackMonitor);