Bug 1508434 - p4: release audio output buffers after processing on task queue. r=jya
☠☠ backed out by ef80c62a3070 ☠ ☠
authorJohn Lin <jolin@mozilla.com>
Wed, 09 Jan 2019 17:40:45 +0000
changeset 510225 1851290ec29bf3e26de182cf91156dbdd571b3cd
parent 510224 12424313d637e32e06fd12a758d14908d0099a15
child 510226 7e107869b00d7ccc5051809d6839be6e98cc4165
push id10547
push userffxbld-merge
push dateMon, 21 Jan 2019 13:03:58 +0000
treeherdermozilla-beta@24ec1916bffe [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjya
bugs1508434
milestone66.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 1508434 - p4: release audio output buffers after processing on task queue. r=jya Differential Revision: https://phabricator.services.mozilla.com/D15985
dom/media/platforms/android/RemoteDataDecoder.cpp
mobile/android/geckoview/src/main/java/org/mozilla/gecko/media/CodecProxy.java
--- a/dom/media/platforms/android/RemoteDataDecoder.cpp
+++ b/dom/media/platforms/android/RemoteDataDecoder.cpp
@@ -27,44 +27,52 @@
 using namespace mozilla;
 using namespace mozilla::gl;
 using namespace mozilla::java;
 using namespace mozilla::java::sdk;
 using media::TimeUnit;
 
 namespace mozilla {
 
-class RemoteVideoDecoder : public RemoteDataDecoder {
+// Hold a reference to the output buffer until we're ready to release it back to
+// the Java codec (for rendering or not).
+class RenderOrReleaseOutput {
  public:
-  // Hold an output buffer and render it to the surface when the frame is sent
-  // to compositor, or release it if not presented.
-  class RenderOrReleaseOutput : public VideoData::Listener {
-   public:
     RenderOrReleaseOutput(CodecProxy::Param aCodec, Sample::Param aSample)
         : mCodec(aCodec), mSample(aSample) {}
 
-    ~RenderOrReleaseOutput() { ReleaseOutput(false); }
+  virtual ~RenderOrReleaseOutput() { ReleaseOutput(false); }
 
-    void OnSentToCompositor() override {
-      ReleaseOutput(true);
-      mCodec = nullptr;
-      mSample = nullptr;
-    }
-
-   private:
+ protected:
     void ReleaseOutput(bool aToRender) {
       if (mCodec && mSample) {
         mCodec->ReleaseOutput(mSample, aToRender);
+      mCodec = nullptr;
+      mSample = nullptr;
       }
     }
 
+ private:
     CodecProxy::GlobalRef mCodec;
     Sample::GlobalRef mSample;
   };
 
+class RemoteVideoDecoder : public RemoteDataDecoder {
+ public:
+  // Render the output to the surface when the frame is sent
+  // to compositor, or release it if not presented.
+  class CompositeListener : private RenderOrReleaseOutput,
+                            public VideoData::Listener {
+   public:
+    CompositeListener(CodecProxy::Param aCodec, Sample::Param aSample)
+        : RenderOrReleaseOutput(aCodec, aSample) {}
+
+    void OnSentToCompositor() override { ReleaseOutput(true); }
+  };
+
   class InputInfo {
    public:
     InputInfo() {}
 
     InputInfo(const int64_t aDurationUs, const gfx::IntSize& aImageSize,
               const gfx::IntSize& aDisplaySize)
         : mDurationUs(aDurationUs),
           mImageSize(aImageSize),
@@ -219,19 +227,20 @@ class RemoteVideoDecoder : public Remote
       MOZ_DIAGNOSTIC_ASSERT(NS_SUCCEEDED(rv));
       Unused << rv;
       return;
     }
 
     AssertOnTaskQueue();
 
     UniquePtr<VideoData::Listener> releaseSample(
-        new RenderOrReleaseOutput(mJavaDecoder, aSample));
+        new CompositeListener(mJavaDecoder, aSample));
 
     BufferInfo::LocalRef info = aSample->Info();
+    MOZ_ASSERT(info);
 
     int32_t flags;
     bool ok = NS_SUCCEEDED(info->Flags(&flags));
 
     int32_t offset;
     ok &= NS_SUCCEEDED(info->Offset(&offset));
 
     int32_t size;
@@ -381,17 +390,20 @@ class RemoteAudioDecoder : public Remote
           &RemoteAudioDecoder::ProcessOutput, std::move(aSample)));
       MOZ_DIAGNOSTIC_ASSERT(NS_SUCCEEDED(rv));
       Unused << rv;
       return;
     }
 
     AssertOnTaskQueue();
 
+    RenderOrReleaseOutput autoRelease(mJavaDecoder, aSample);
+
     BufferInfo::LocalRef info = aSample->Info();
+    MOZ_ASSERT(info);
 
     int32_t flags;
     bool ok = NS_SUCCEEDED(info->Flags(&flags));
 
     int32_t offset;
     ok &= NS_SUCCEEDED(info->Offset(&offset));
 
     int64_t presentationTimeUs;
--- a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/media/CodecProxy.java
+++ b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/media/CodecProxy.java
@@ -89,27 +89,18 @@ public final class CodecProxy {
         public synchronized void onOutput(Sample sample) throws RemoteException {
             if (mCodecProxyReleased) {
                 sample.dispose();
                 return;
             }
             if (mOutputSurface != null) {
                 // Don't render to surface just yet. Callback will make that happen when it's time.
                 mSurfaceOutputs.offer(sample);
-                mCallbacks.onOutput(sample);
-            } else {
-                // Non-surface output needs no rendering.
-                try {
-                    mCallbacks.onOutput(sample);
-                    mRemote.releaseOutput(sample, false);
-                    sample.dispose();
-                } catch (Exception e) {
-                    reportError(true);
-                }
             }
+            mCallbacks.onOutput(sample);
         }
 
         @Override
         public void onError(boolean fatal) throws RemoteException {
             reportError(fatal);
         }
 
         private synchronized void reportError(boolean fatal) {