[FFmpeg-devel] [PATCH] lavf/mov.c: Fallback to finding non-keyframe in fix_index, if keyframe search fails.

Sasi Inguva isasi at google.com
Thu Nov 3 21:39:56 EET 2016


Signed-off-by: Sasi Inguva <isasi at google.com>
---
 libavformat/mov.c  | 30 ++++++++++++++++++++----------
 tests/fate/mov.mak |  6 +++++-
 2 files changed, 25 insertions(+), 11 deletions(-)

diff --git a/libavformat/mov.c b/libavformat/mov.c
index 4222088..f5b2035 100644
--- a/libavformat/mov.c
+++ b/libavformat/mov.c
@@ -2805,16 +2805,17 @@ static int get_edit_list_entry(MOVContext *mov,
 }
 
 /**
- * Find the closest previous keyframe to the timestamp, in e_old index
- * entries.
+ * Find the closest previous frame to the timestamp, in e_old index
+ * entries. Searching for just any frame / just key frames can be controlled by
+ * last argument 'flag'.
  * Returns the index of the entry in st->index_entries if successful,
  * else returns -1.
  */
-static int64_t find_prev_closest_keyframe_index(AVStream *st,
-                                                AVIndexEntry *e_old,
-                                                int nb_old,
-                                                int64_t timestamp,
-                                                int flag)
+static int64_t find_prev_closest_index(AVStream *st,
+                                       AVIndexEntry *e_old,
+                                       int nb_old,
+                                       int64_t timestamp,
+                                       int flag)
 {
     AVIndexEntry *e_keep = st->index_entries;
     int nb_keep = st->nb_index_entries;
@@ -3031,10 +3032,19 @@ static void mov_fix_index(MOVContext *mov, AVStream *st)
             search_timestamp = FFMAX(search_timestamp - msc->time_scale, e_old[0].timestamp);
         }
 
-        index = find_prev_closest_keyframe_index(st, e_old, nb_old, search_timestamp, 0);
+        index = find_prev_closest_index(st, e_old, nb_old, search_timestamp, 0);
         if (index == -1) {
-            av_log(mov->fc, AV_LOG_ERROR, "Missing key frame while reordering index according to edit list\n");
-            continue;
+            av_log(mov->fc, AV_LOG_WARNING,
+                   "st: %d edit list: %"PRId64" Missing key frame while searching for timestamp: %"PRId64"\n",
+                   st->index, edit_list_index, search_timestamp);
+            index = find_prev_closest_index(st, e_old, nb_old, search_timestamp, AVSEEK_FLAG_ANY);
+
+            if (index == -1) {
+                av_log(mov->fc, AV_LOG_ERROR,
+                       "st: %d edit list %"PRId64" Cannot find an index entry before timestamp: %"PRId64"\n",
+                       st->index, edit_list_index, search_timestamp);
+                continue;
+            }
         }
         current = e_old + index;
 
diff --git a/tests/fate/mov.mak b/tests/fate/mov.mak
index 6b79832..b6ecbfc 100644
--- a/tests/fate/mov.mak
+++ b/tests/fate/mov.mak
@@ -5,7 +5,8 @@ FATE_MOV = fate-mov-3elist \
            fate-mov-elist-starts-ctts-2ndsample \
            fate-mov-1elist-ends-last-bframe \
            fate-mov-2elist-elist1-ends-bframe \
-           fate-mov-aac-2048-priming
+           fate-mov-aac-2048-priming \
+	   fate-mp4-init-nonkeyframe
 
 FATE_SAMPLES_AVCONV += $(FATE_MOV)
 
@@ -30,3 +31,6 @@ fate-mov-2elist-elist1-ends-bframe: CMD = framemd5 -i $(TARGET_SAMPLES)/mov/mov-
 
 fate-mov-aac-2048-priming: ffprobe$(PROGSSUF)$(EXESUF)
 fate-mov-aac-2048-priming: CMD = run ffprobe$(PROGSSUF)$(EXESUF) -show_packets -print_format compact $(TARGET_SAMPLES)/mov/aac-2048-priming.mov
+
+fate-mp4-init-nonkeyframe: ffprobe$(PROGSSUF)$(EXESUF)
+fate-mp4-init-nonkeyframe: CMD = run ffprobe$(PROGSSUF)$(EXESUF) -show_packets -print_format compact -select_streams v $(TARGET_SAMPLES)/mov/mp4-init-nonkeyframe.mp4
-- 
2.8.0.rc3.226.g39d4020



More information about the ffmpeg-devel mailing list