Search in sources :

Example 1 with DecoderException

use of com.google.android.exoplayer2.decoder.DecoderException in project ExoPlayer by google.

the class DecoderAudioRenderer method maybeInitDecoder.

private void maybeInitDecoder() throws ExoPlaybackException {
    if (decoder != null) {
        return;
    }
    setDecoderDrmSession(sourceDrmSession);
    CryptoConfig cryptoConfig = null;
    if (decoderDrmSession != null) {
        cryptoConfig = decoderDrmSession.getCryptoConfig();
        if (cryptoConfig == null) {
            DrmSessionException drmError = decoderDrmSession.getError();
            if (drmError != null) {
            // Continue for now. We may be able to avoid failure if a new input format causes the
            // session to be replaced without it having been used.
            } else {
                // The drm session isn't open yet.
                return;
            }
        }
    }
    try {
        long codecInitializingTimestamp = SystemClock.elapsedRealtime();
        TraceUtil.beginSection("createAudioDecoder");
        decoder = createDecoder(inputFormat, cryptoConfig);
        TraceUtil.endSection();
        long codecInitializedTimestamp = SystemClock.elapsedRealtime();
        eventDispatcher.decoderInitialized(decoder.getName(), codecInitializedTimestamp, codecInitializedTimestamp - codecInitializingTimestamp);
        decoderCounters.decoderInitCount++;
    } catch (DecoderException e) {
        Log.e(TAG, "Audio codec error", e);
        eventDispatcher.audioCodecError(e);
        throw createRendererException(e, inputFormat, PlaybackException.ERROR_CODE_DECODER_INIT_FAILED);
    } catch (OutOfMemoryError e) {
        throw createRendererException(e, inputFormat, PlaybackException.ERROR_CODE_DECODER_INIT_FAILED);
    }
}
Also used : DecoderException(com.google.android.exoplayer2.decoder.DecoderException) DrmSessionException(com.google.android.exoplayer2.drm.DrmSession.DrmSessionException) CryptoConfig(com.google.android.exoplayer2.decoder.CryptoConfig)

Example 2 with DecoderException

use of com.google.android.exoplayer2.decoder.DecoderException in project ExoPlayer by google.

the class DecoderAudioRenderer method render.

@Override
public void render(long positionUs, long elapsedRealtimeUs) throws ExoPlaybackException {
    if (outputStreamEnded) {
        try {
            audioSink.playToEndOfStream();
        } catch (AudioSink.WriteException e) {
            throw createRendererException(e, e.format, e.isRecoverable, PlaybackException.ERROR_CODE_AUDIO_TRACK_WRITE_FAILED);
        }
        return;
    }
    // Try and read a format if we don't have one already.
    if (inputFormat == null) {
        // We don't have a format yet, so try and read one.
        FormatHolder formatHolder = getFormatHolder();
        flagsOnlyBuffer.clear();
        @ReadDataResult int result = readSource(formatHolder, flagsOnlyBuffer, FLAG_REQUIRE_FORMAT);
        if (result == C.RESULT_FORMAT_READ) {
            onInputFormatChanged(formatHolder);
        } else if (result == C.RESULT_BUFFER_READ) {
            // End of stream read having not read a format.
            Assertions.checkState(flagsOnlyBuffer.isEndOfStream());
            inputStreamEnded = true;
            try {
                processEndOfStream();
            } catch (AudioSink.WriteException e) {
                throw createRendererException(e, /* format= */
                null, PlaybackException.ERROR_CODE_AUDIO_TRACK_WRITE_FAILED);
            }
            return;
        } else {
            // We still don't have a format and can't make progress without one.
            return;
        }
    }
    // If we don't have a decoder yet, we need to instantiate one.
    maybeInitDecoder();
    if (decoder != null) {
        try {
            // Rendering loop.
            TraceUtil.beginSection("drainAndFeed");
            while (drainOutputBuffer()) {
            }
            while (feedInputBuffer()) {
            }
            TraceUtil.endSection();
        } catch (DecoderException e) {
            // Can happen with dequeueOutputBuffer, dequeueInputBuffer, queueInputBuffer
            Log.e(TAG, "Audio codec error", e);
            eventDispatcher.audioCodecError(e);
            throw createRendererException(e, inputFormat, PlaybackException.ERROR_CODE_DECODING_FAILED);
        } catch (AudioSink.ConfigurationException e) {
            throw createRendererException(e, e.format, PlaybackException.ERROR_CODE_AUDIO_TRACK_INIT_FAILED);
        } catch (AudioSink.InitializationException e) {
            throw createRendererException(e, e.format, e.isRecoverable, PlaybackException.ERROR_CODE_AUDIO_TRACK_INIT_FAILED);
        } catch (AudioSink.WriteException e) {
            throw createRendererException(e, e.format, e.isRecoverable, PlaybackException.ERROR_CODE_AUDIO_TRACK_WRITE_FAILED);
        }
        decoderCounters.ensureUpdated();
    }
}
Also used : DecoderException(com.google.android.exoplayer2.decoder.DecoderException) ReadDataResult(com.google.android.exoplayer2.source.SampleStream.ReadDataResult) FormatHolder(com.google.android.exoplayer2.FormatHolder)

Example 3 with DecoderException

use of com.google.android.exoplayer2.decoder.DecoderException in project ExoPlayer by google.

the class DecoderAudioRenderer method feedInputBuffer.

private boolean feedInputBuffer() throws DecoderException, ExoPlaybackException {
    if (decoder == null || decoderReinitializationState == REINITIALIZATION_STATE_WAIT_END_OF_STREAM || inputStreamEnded) {
        // We need to reinitialize the decoder or the input stream has ended.
        return false;
    }
    if (inputBuffer == null) {
        inputBuffer = decoder.dequeueInputBuffer();
        if (inputBuffer == null) {
            return false;
        }
    }
    if (decoderReinitializationState == REINITIALIZATION_STATE_SIGNAL_END_OF_STREAM) {
        inputBuffer.setFlags(C.BUFFER_FLAG_END_OF_STREAM);
        decoder.queueInputBuffer(inputBuffer);
        inputBuffer = null;
        decoderReinitializationState = REINITIALIZATION_STATE_WAIT_END_OF_STREAM;
        return false;
    }
    FormatHolder formatHolder = getFormatHolder();
    switch(readSource(formatHolder, inputBuffer, /* readFlags= */
    0)) {
        case C.RESULT_NOTHING_READ:
            return false;
        case C.RESULT_FORMAT_READ:
            onInputFormatChanged(formatHolder);
            return true;
        case C.RESULT_BUFFER_READ:
            if (inputBuffer.isEndOfStream()) {
                inputStreamEnded = true;
                decoder.queueInputBuffer(inputBuffer);
                inputBuffer = null;
                return false;
            }
            inputBuffer.flip();
            inputBuffer.format = inputFormat;
            onQueueInputBuffer(inputBuffer);
            decoder.queueInputBuffer(inputBuffer);
            decoderReceivedBuffers = true;
            decoderCounters.queuedInputBufferCount++;
            inputBuffer = null;
            return true;
        default:
            throw new IllegalStateException();
    }
}
Also used : FormatHolder(com.google.android.exoplayer2.FormatHolder)

Example 4 with DecoderException

use of com.google.android.exoplayer2.decoder.DecoderException in project ExoPlayer by google.

the class DecoderVideoRenderer method processOutputBuffer.

/**
 * Processes {@link #outputBuffer} by rendering it, skipping it or doing nothing, and returns
 * whether it may be possible to process another output buffer.
 *
 * @param positionUs The player's current position.
 * @param elapsedRealtimeUs {@link android.os.SystemClock#elapsedRealtime()} in microseconds,
 *     measured at the start of the current iteration of the rendering loop.
 * @return Whether it may be possible to drain another output buffer.
 * @throws ExoPlaybackException If an error occurs processing the output buffer.
 */
private boolean processOutputBuffer(long positionUs, long elapsedRealtimeUs) throws ExoPlaybackException, DecoderException {
    if (initialPositionUs == C.TIME_UNSET) {
        initialPositionUs = positionUs;
    }
    long earlyUs = outputBuffer.timeUs - positionUs;
    if (!hasOutput()) {
        // Skip frames in sync with playback, so we'll be at the right frame if the mode changes.
        if (isBufferLate(earlyUs)) {
            skipOutputBuffer(outputBuffer);
            return true;
        }
        return false;
    }
    long presentationTimeUs = outputBuffer.timeUs - outputStreamOffsetUs;
    Format format = formatQueue.pollFloor(presentationTimeUs);
    if (format != null) {
        outputFormat = format;
    }
    long elapsedRealtimeNowUs = SystemClock.elapsedRealtime() * 1000;
    long elapsedSinceLastRenderUs = elapsedRealtimeNowUs - lastRenderTimeUs;
    boolean isStarted = getState() == STATE_STARTED;
    boolean shouldRenderFirstFrame = !renderedFirstFrameAfterEnable ? (isStarted || mayRenderFirstFrameAfterEnableIfNotStarted) : !renderedFirstFrameAfterReset;
    // TODO: We shouldn't force render while we are joining an ongoing playback.
    if (shouldRenderFirstFrame || (isStarted && shouldForceRenderOutputBuffer(earlyUs, elapsedSinceLastRenderUs))) {
        renderOutputBuffer(outputBuffer, presentationTimeUs, outputFormat);
        return true;
    }
    if (!isStarted || positionUs == initialPositionUs) {
        return false;
    }
    // TODO: Treat dropped buffers as skipped while we are joining an ongoing playback.
    if (shouldDropBuffersToKeyframe(earlyUs, elapsedRealtimeUs) && maybeDropBuffersToKeyframe(positionUs)) {
        return false;
    } else if (shouldDropOutputBuffer(earlyUs, elapsedRealtimeUs)) {
        dropOutputBuffer(outputBuffer);
        return true;
    }
    if (earlyUs < 30000) {
        renderOutputBuffer(outputBuffer, presentationTimeUs, outputFormat);
        return true;
    }
    return false;
}
Also used : Format(com.google.android.exoplayer2.Format)

Example 5 with DecoderException

use of com.google.android.exoplayer2.decoder.DecoderException in project ExoPlayer by google.

the class DecoderVideoRenderer method maybeInitDecoder.

private void maybeInitDecoder() throws ExoPlaybackException {
    if (decoder != null) {
        return;
    }
    setDecoderDrmSession(sourceDrmSession);
    CryptoConfig cryptoConfig = null;
    if (decoderDrmSession != null) {
        cryptoConfig = decoderDrmSession.getCryptoConfig();
        if (cryptoConfig == null) {
            DrmSessionException drmError = decoderDrmSession.getError();
            if (drmError != null) {
            // Continue for now. We may be able to avoid failure if a new input format causes the
            // session to be replaced without it having been used.
            } else {
                // The drm session isn't open yet.
                return;
            }
        }
    }
    try {
        long decoderInitializingTimestamp = SystemClock.elapsedRealtime();
        decoder = createDecoder(inputFormat, cryptoConfig);
        setDecoderOutputMode(outputMode);
        long decoderInitializedTimestamp = SystemClock.elapsedRealtime();
        eventDispatcher.decoderInitialized(decoder.getName(), decoderInitializedTimestamp, decoderInitializedTimestamp - decoderInitializingTimestamp);
        decoderCounters.decoderInitCount++;
    } catch (DecoderException e) {
        Log.e(TAG, "Video codec error", e);
        eventDispatcher.videoCodecError(e);
        throw createRendererException(e, inputFormat, PlaybackException.ERROR_CODE_DECODER_INIT_FAILED);
    } catch (OutOfMemoryError e) {
        throw createRendererException(e, inputFormat, PlaybackException.ERROR_CODE_DECODER_INIT_FAILED);
    }
}
Also used : DecoderException(com.google.android.exoplayer2.decoder.DecoderException) DrmSessionException(com.google.android.exoplayer2.drm.DrmSession.DrmSessionException) CryptoConfig(com.google.android.exoplayer2.decoder.CryptoConfig)

Aggregations

DecoderException (com.google.android.exoplayer2.decoder.DecoderException)5 FormatHolder (com.google.android.exoplayer2.FormatHolder)4 Format (com.google.android.exoplayer2.Format)3 CryptoConfig (com.google.android.exoplayer2.decoder.CryptoConfig)3 DrmSessionException (com.google.android.exoplayer2.drm.DrmSession.DrmSessionException)2 ReadDataResult (com.google.android.exoplayer2.source.SampleStream.ReadDataResult)2 SurfaceTexture (android.graphics.SurfaceTexture)1 Handler (android.os.Handler)1 Surface (android.view.Surface)1 Nullable (androidx.annotation.Nullable)1 RendererCapabilities (com.google.android.exoplayer2.RendererCapabilities)1 DecoderInputBuffer (com.google.android.exoplayer2.decoder.DecoderInputBuffer)1 SimpleDecoder (com.google.android.exoplayer2.decoder.SimpleDecoder)1 VideoDecoderOutputBuffer (com.google.android.exoplayer2.decoder.VideoDecoderOutputBuffer)1 Phaser (java.util.concurrent.Phaser)1 Before (org.junit.Before)1