From c8e5988e6d2ca8c2391042adb2f3ea0443f937f3 Mon Sep 17 00:00:00 2001 From: Oliver Woodman Date: Fri, 5 Dec 2014 17:53:24 +0000 Subject: [PATCH] Fix handling of unknown duration in FMP4. Issue: 186 --- .../parser/mp4/FragmentedMp4Extractor.java | 21 +++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/library/src/main/java/com/google/android/exoplayer/parser/mp4/FragmentedMp4Extractor.java b/library/src/main/java/com/google/android/exoplayer/parser/mp4/FragmentedMp4Extractor.java index c9d2caf953..9950aecd2a 100644 --- a/library/src/main/java/com/google/android/exoplayer/parser/mp4/FragmentedMp4Extractor.java +++ b/library/src/main/java/com/google/android/exoplayer/parser/mp4/FragmentedMp4Extractor.java @@ -462,7 +462,8 @@ public final class FragmentedMp4Extractor implements Extractor { /** * Parses a tkhd atom (defined in 14496-12). * - * @return A {@link Pair} consisting of the track id and duration. + * @return A {@link Pair} consisting of the track id and duration (in the timescale indicated in + * the movie header box). The duration is set to -1 if the duration is unspecified. */ private static Pair parseTkhd(ParsableByteArray tkhd) { tkhd.setPosition(ATOM_HEADER_SIZE); @@ -473,7 +474,23 @@ public final class FragmentedMp4Extractor implements Extractor { int trackId = tkhd.readInt(); tkhd.skip(4); - long duration = version == 0 ? tkhd.readUnsignedInt() : tkhd.readUnsignedLongToLong(); + + boolean durationUnknown = true; + int durationPosition = tkhd.getPosition(); + int durationByteCount = version == 0 ? 4 : 8; + for (int i = 0; i < durationByteCount; i++) { + if (tkhd.data[durationPosition + i] != -1) { + durationUnknown = false; + break; + } + } + long duration; + if (durationUnknown) { + tkhd.skip(durationByteCount); + duration = -1; + } else { + duration = version == 0 ? tkhd.readUnsignedInt() : tkhd.readUnsignedLongToLong(); + } return Pair.create(trackId, duration); }