[FFmpeg-devel] [PATCH 13/17] avformat/avc: Remove trailing zero bytes during annex B->mp4 conversion

Andreas Rheinhardt andreas.rheinhardt at gmail.com
Thu Jul 9 22:20:18 EEST 2020


The annex B format of H.264 and HEVC allows there to be trailing zero
bytes in byte stream NAL units; this means that there can be trailing
zero bytes after the actual NAL units (besides start codes
prepended to them).

Samples in mp4 contain a sequence of length-prefixed NAL units and not
byte stream NAL units; as such, the trailing zero bytes are actually
not allowed. Therefore this commit strips them away.

Two fate-tests needed to be updated: hevc-bsf-mp4toannexb because the
HEVC parser does not properly check for four byte startcodes and instead
assigns the leading zero to the end of the preceding packet (it is now
stripped away) and lavf-fate-h264.mp4 because of an oddity of
ff_h2645_extract_rbsp: It also assigns the first byte of a four-byte
startcode to the preceding unit and this meant that the extradata (from
the extract extradata bsf) has a trailing zero at the end which is now
discarded.

Signed-off-by: Andreas Rheinhardt <andreas.rheinhardt at gmail.com>
---
 libavformat/avc.c            | 11 +++++++----
 tests/fate/hevc.mak          |  2 +-
 tests/ref/lavf-fate/h264.mp4 |  4 ++--
 3 files changed, 10 insertions(+), 7 deletions(-)

diff --git a/libavformat/avc.c b/libavformat/avc.c
index 17fcd1e73f..9f375ca992 100644
--- a/libavformat/avc.c
+++ b/libavformat/avc.c
@@ -92,7 +92,7 @@ const uint8_t *ff_avc_find_startcode(const uint8_t *p, const uint8_t *end){
 const uint8_t *ff_avc_parse_nalu(const uint8_t **start, const uint8_t **nal_end,
                                  const uint8_t *end)
 {
-    const uint8_t *p = *start, *next;
+    const uint8_t *p = *start, *next, *end_temp;
 
     if (!p)
         return NULL;
@@ -108,18 +108,21 @@ search_again:
     next = avc_find_startcode_internal(p, end);
 
     if (next) {
-        *nal_end = next > p && !next[-1] ? next - 1 : next;
+        end_temp = next;
         next    += 3;
     } else {
-        *nal_end = end;
+        end_temp = end;
     }
-    if (*nal_end == p) {
+    while (end_temp > p && !end_temp[-1])
+        end_temp--;
+    if (end_temp == p) {
         if (!next)
             return NULL;
         p = next;
         goto search_again;
     }
     *start = next;
+    *nal_end = end_temp;
     return p;
 }
 
diff --git a/tests/fate/hevc.mak b/tests/fate/hevc.mak
index 65c5a262e9..bd94cc6cff 100644
--- a/tests/fate/hevc.mak
+++ b/tests/fate/hevc.mak
@@ -251,7 +251,7 @@ FATE_HEVC-$(call ALLYES, HEVC_DEMUXER MOV_DEMUXER HEVC_MP4TOANNEXB_BSF MOV_MUXER
 fate-hevc-bsf-mp4toannexb: tests/data/hevc-mp4.mov
 fate-hevc-bsf-mp4toannexb: CMD = md5 -i $(TARGET_PATH)/tests/data/hevc-mp4.mov -c:v copy -fflags +bitexact -f hevc
 fate-hevc-bsf-mp4toannexb: CMP = oneline
-fate-hevc-bsf-mp4toannexb: REF = 1873662a3af1848c37e4eb25722c8df9
+fate-hevc-bsf-mp4toannexb: REF = 73019329ed7f81c24f9af67c34c640c0
 
 fate-hevc-skiploopfilter: CMD = framemd5 -skip_loop_filter nokey -i $(TARGET_SAMPLES)/hevc-conformance/SAO_D_Samsung_5.bit -sws_flags bitexact
 FATE_HEVC += fate-hevc-skiploopfilter
diff --git a/tests/ref/lavf-fate/h264.mp4 b/tests/ref/lavf-fate/h264.mp4
index bb52f45758..7a84b7a983 100644
--- a/tests/ref/lavf-fate/h264.mp4
+++ b/tests/ref/lavf-fate/h264.mp4
@@ -1,3 +1,3 @@
-6d158b25efe7391c803f6f61c7a80aa0 *tests/data/lavf-fate/lavf.h264.mp4
-547908 tests/data/lavf-fate/lavf.h264.mp4
+aaf8b3d9340ab1fdebced54ada2447d5 *tests/data/lavf-fate/lavf.h264.mp4
+547907 tests/data/lavf-fate/lavf.h264.mp4
 tests/data/lavf-fate/lavf.h264.mp4 CRC=0x9da2c999
-- 
2.20.1



More information about the ffmpeg-devel mailing list