From efaea811941c009ed09ebd6556596e059afd7e9c Mon Sep 17 00:00:00 2001 From: olly Date: Fri, 13 May 2016 07:47:40 -0700 Subject: [PATCH] Use CodecCounters consistently in all renderers. - Increment skippedBufferCount for VPX and ADTR. - Set maxConsecutiveDroppedOutputBufferCount count for VPX. Tweak its meaning to ignore skipped frames. - Remove outputFormat/outputBuffer changed counts. These add limited value. Also, MediaCodec is moving toward a model where you don't see the output buffers changing because you dequeue them one at a time (like how our extension decoders work). ------------- Created by MOE: https://github.com/google/moe MOE_MIGRATED_REVID=122258530 --- .../ext/vp9/LibvpxVideoTrackRenderer.java | 9 +++- .../android/exoplayer/CodecCounters.java | 46 ++++++++++++++----- .../exoplayer/MediaCodecTrackRenderer.java | 2 - .../MediaCodecVideoTrackRenderer.java | 6 +-- .../extensions/AudioDecoderTrackRenderer.java | 1 + .../exoplayer/extensions/OutputBuffer.java | 5 ++ .../exoplayer/extensions/SimpleDecoder.java | 17 ++++--- 7 files changed, 62 insertions(+), 24 deletions(-) diff --git a/extensions/vp9/src/main/java/com/google/android/exoplayer/ext/vp9/LibvpxVideoTrackRenderer.java b/extensions/vp9/src/main/java/com/google/android/exoplayer/ext/vp9/LibvpxVideoTrackRenderer.java index 670599908a..0f62a71cd0 100644 --- a/extensions/vp9/src/main/java/com/google/android/exoplayer/ext/vp9/LibvpxVideoTrackRenderer.java +++ b/extensions/vp9/src/main/java/com/google/android/exoplayer/ext/vp9/LibvpxVideoTrackRenderer.java @@ -79,8 +79,9 @@ public final class LibvpxVideoTrackRenderer extends TrackRenderer { private int previousWidth; private int previousHeight; - private int droppedFrameCount; private long droppedFrameAccumulationStartTimeMs; + private int droppedFrameCount; + private int consecutiveDroppedFrameCount; /** * @param scaleToFit Boolean that indicates if video frames should be scaled to fit when @@ -183,6 +184,7 @@ public final class LibvpxVideoTrackRenderer extends TrackRenderer { if (outputBuffer == null) { return false; } + codecCounters.skippedOutputBufferCount += outputBuffer.skippedOutputBufferCount; } if (nextOutputBuffer == null) { @@ -202,6 +204,9 @@ public final class LibvpxVideoTrackRenderer extends TrackRenderer { // Drop frame if we are too late. codecCounters.droppedOutputBufferCount++; droppedFrameCount++; + consecutiveDroppedFrameCount++; + codecCounters.maxConsecutiveDroppedOutputBufferCount = Math.max(consecutiveDroppedFrameCount, + codecCounters.maxConsecutiveDroppedOutputBufferCount); if (droppedFrameCount == maxDroppedFrameCountToNotify) { notifyAndResetDroppedFrameCount(); } @@ -227,6 +232,7 @@ public final class LibvpxVideoTrackRenderer extends TrackRenderer { private void renderBuffer() { codecCounters.renderedOutputBufferCount++; + consecutiveDroppedFrameCount = 0; notifyIfVideoSizeChanged(outputBuffer.width, outputBuffer.height); if (outputBuffer.mode == VpxDecoder.OUTPUT_MODE_RGB && surface != null) { renderRgbFrame(outputBuffer, scaleToFit); @@ -320,6 +326,7 @@ public final class LibvpxVideoTrackRenderer extends TrackRenderer { inputStreamEnded = false; outputStreamEnded = false; renderedFirstFrame = false; + consecutiveDroppedFrameCount = 0; if (decoder != null) { flushDecoder(); } diff --git a/library/src/main/java/com/google/android/exoplayer/CodecCounters.java b/library/src/main/java/com/google/android/exoplayer/CodecCounters.java index 3a35234822..0b45574a25 100644 --- a/library/src/main/java/com/google/android/exoplayer/CodecCounters.java +++ b/library/src/main/java/com/google/android/exoplayer/CodecCounters.java @@ -24,14 +24,40 @@ package com.google.android.exoplayer; */ public final class CodecCounters { + /** + * The number of times the codec has been initialized. + */ public int codecInitCount; + /** + * The number of times the codec has been released. + */ public int codecReleaseCount; + /** + * The number of queued input buffers. + */ public int inputBufferCount; - public int outputFormatChangedCount; - public int outputBuffersChangedCount; + /** + * The number of rendered output buffers. + */ public int renderedOutputBufferCount; + /** + * The number of skipped output buffers. + *

+ * A skipped output buffer is an output buffer that was deliberately not rendered. + */ public int skippedOutputBufferCount; + /** + * The number of dropped output buffers. + *

+ * A dropped output buffer is an output buffer that was supposed to be rendered, but was instead + * dropped because it could not be rendered in time. + */ public int droppedOutputBufferCount; + /** + * The maximum number of dropped output buffers without an interleaving rendered output buffer. + *

+ * Skipped output buffers are ignored for the purposes of calculating this value. + */ public int maxConsecutiveDroppedOutputBufferCount; /** @@ -46,15 +72,13 @@ public final class CodecCounters { public String getDebugString() { ensureUpdated(); - return "cic:" + codecInitCount - + " crc:" + codecReleaseCount - + " ibc:" + inputBufferCount - + " ofc:" + outputFormatChangedCount - + " obc:" + outputBuffersChangedCount - + " ren:" + renderedOutputBufferCount - + " sob:" + skippedOutputBufferCount - + " dob:" + droppedOutputBufferCount - + " mcdob:" + maxConsecutiveDroppedOutputBufferCount; + return "ic:" + codecInitCount + + " rc:" + codecReleaseCount + + " ib:" + inputBufferCount + + " rb:" + renderedOutputBufferCount + + " sb:" + skippedOutputBufferCount + + " db:" + droppedOutputBufferCount + + " mcdb:" + maxConsecutiveDroppedOutputBufferCount; } } diff --git a/library/src/main/java/com/google/android/exoplayer/MediaCodecTrackRenderer.java b/library/src/main/java/com/google/android/exoplayer/MediaCodecTrackRenderer.java index 9d2632c979..7029dc2905 100644 --- a/library/src/main/java/com/google/android/exoplayer/MediaCodecTrackRenderer.java +++ b/library/src/main/java/com/google/android/exoplayer/MediaCodecTrackRenderer.java @@ -827,7 +827,6 @@ public abstract class MediaCodecTrackRenderer extends TrackRenderer { format.setInteger(android.media.MediaFormat.KEY_CHANNEL_COUNT, 1); } onOutputFormatChanged(codec, format); - codecCounters.outputFormatChangedCount++; } /** @@ -836,7 +835,6 @@ public abstract class MediaCodecTrackRenderer extends TrackRenderer { @SuppressWarnings("deprecation") private void processOutputBuffersChanged() { outputBuffers = codec.getOutputBuffers(); - codecCounters.outputBuffersChangedCount++; } /** diff --git a/library/src/main/java/com/google/android/exoplayer/MediaCodecVideoTrackRenderer.java b/library/src/main/java/com/google/android/exoplayer/MediaCodecVideoTrackRenderer.java index f58983c7e0..245258bc78 100644 --- a/library/src/main/java/com/google/android/exoplayer/MediaCodecVideoTrackRenderer.java +++ b/library/src/main/java/com/google/android/exoplayer/MediaCodecVideoTrackRenderer.java @@ -392,7 +392,6 @@ public class MediaCodecVideoTrackRenderer extends MediaCodecTrackRenderer { boolean shouldSkip) { if (shouldSkip) { skipOutputBuffer(codec, bufferIndex); - consecutiveDroppedFrameCount = 0; return true; } @@ -402,7 +401,6 @@ public class MediaCodecVideoTrackRenderer extends MediaCodecTrackRenderer { } else { renderOutputBuffer(codec, bufferIndex); } - consecutiveDroppedFrameCount = 0; return true; } @@ -433,7 +431,6 @@ public class MediaCodecVideoTrackRenderer extends MediaCodecTrackRenderer { // Let the underlying framework time the release. if (earlyUs < 50000) { renderOutputBufferV21(codec, bufferIndex, adjustedReleaseTimeNs); - consecutiveDroppedFrameCount = 0; return true; } } else { @@ -450,7 +447,6 @@ public class MediaCodecVideoTrackRenderer extends MediaCodecTrackRenderer { } } renderOutputBuffer(codec, bufferIndex); - consecutiveDroppedFrameCount = 0; return true; } } @@ -486,6 +482,7 @@ public class MediaCodecVideoTrackRenderer extends MediaCodecTrackRenderer { codec.releaseOutputBuffer(bufferIndex, true); TraceUtil.endSection(); codecCounters.renderedOutputBufferCount++; + consecutiveDroppedFrameCount = 0; renderedFirstFrame = true; maybeNotifyDrawnToSurface(); } @@ -497,6 +494,7 @@ public class MediaCodecVideoTrackRenderer extends MediaCodecTrackRenderer { codec.releaseOutputBuffer(bufferIndex, releaseTimeNs); TraceUtil.endSection(); codecCounters.renderedOutputBufferCount++; + consecutiveDroppedFrameCount = 0; renderedFirstFrame = true; maybeNotifyDrawnToSurface(); } diff --git a/library/src/main/java/com/google/android/exoplayer/extensions/AudioDecoderTrackRenderer.java b/library/src/main/java/com/google/android/exoplayer/extensions/AudioDecoderTrackRenderer.java index b4629ca03b..b12ee12c9d 100644 --- a/library/src/main/java/com/google/android/exoplayer/extensions/AudioDecoderTrackRenderer.java +++ b/library/src/main/java/com/google/android/exoplayer/extensions/AudioDecoderTrackRenderer.java @@ -164,6 +164,7 @@ public abstract class AudioDecoderTrackRenderer extends TrackRenderer implements if (outputBuffer == null) { return false; } + codecCounters.skippedOutputBufferCount += outputBuffer.skippedOutputBufferCount; } if (outputBuffer.isEndOfStream()) { diff --git a/library/src/main/java/com/google/android/exoplayer/extensions/OutputBuffer.java b/library/src/main/java/com/google/android/exoplayer/extensions/OutputBuffer.java index f2eb9a53db..dd6896bb26 100644 --- a/library/src/main/java/com/google/android/exoplayer/extensions/OutputBuffer.java +++ b/library/src/main/java/com/google/android/exoplayer/extensions/OutputBuffer.java @@ -27,6 +27,11 @@ public abstract class OutputBuffer extends Buffer { */ public long timestampUs; + /** + * The number of buffers immediately prior to this one that were skipped in the {@link Decoder}. + */ + public int skippedOutputBufferCount; + /** * Releases the output buffer for reuse. Must be called when the buffer is no longer needed. */ diff --git a/library/src/main/java/com/google/android/exoplayer/extensions/SimpleDecoder.java b/library/src/main/java/com/google/android/exoplayer/extensions/SimpleDecoder.java index 20809d0cd6..0bdcfccf2a 100644 --- a/library/src/main/java/com/google/android/exoplayer/extensions/SimpleDecoder.java +++ b/library/src/main/java/com/google/android/exoplayer/extensions/SimpleDecoder.java @@ -56,6 +56,7 @@ public abstract class SimpleDecoder