Я принимаю поток RTMP и преобразую его в фрагментированный файл MP4 в JavaScript.Прошла неделя работы, но я почти закончил с этим заданием.Я генерирую действительный ftyp
атом, moov
атом и moof
атом, и первый кадр видео фактически воспроизводится (со звуком), прежде чем оно перейдет в бесконечную буферизацию без ошибок, перечисленных в chrome://media-internals
При подключении видео к ffprobe
я получаю ошибку, похожую на:
[mov,mp4,m4a,3gp,3g2,mj2 @ 0x558559198080] Failed to add index entry
Last message repeated 368 times
[h264 @ 0x55855919b300] Invalid NAL unit size (-619501801 > 966).
[h264 @ 0x55855919b300] Error splitting the input into NAL units.
Это привело меня к массовой охоте на проблемы с выравниванием данных или недопустимыми смещениями байтов в моих tfhd
иtrun
атомов, однако независимо от того, где я смотрел или как я нарезал данные, я не мог найти никаких проблем в moof
атоме.
Затем я взял исходный файл FLV и преобразовал его вMP4 в ffmpeg
с помощью следующей команды:
ffmpeg -i ~/Videos/rtmp/big_buck_bunny.flv -c copy -ss 5 -t 10 -movflags frag_keyframe+empty_moov+faststart test.mp4
Я открыл как созданный мною MP4, так и вывод MP4 с помощью ffmpeg
в файле синтаксического анализа атомов и сравнил их:
Первое, что бросилось в глаза, было то, что сгенерированный ffmpeg
файл имеет несколько сэмплов видео на moof
.В частности, каждый moof
начинался с 1 ключевого кадра, затем содержал все разностные кадры до следующего ключевого кадра (который использовался в качестве начала следующего moof
атома)
Сравните это с тем, как яГенерация моего MP4.Я создаю moof
атом каждый раз, когда приходит пакет FLV VIDEODATA
.Это означает, что мой moof
может не содержать ключевой кадр (и обычно его нет)
Может быть, поэтому у меня возникли проблемы?Или я пропускаю что-то еще?
Видеофайлы, о которых идет речь, можно скачать здесь:
Еще одна проблема, которую я заметил, - это активное использование ffmpeg
base_data_offset
в tfhd
атом.Однако, когда я попытался отследить общее число добавленных байтов и сам установить base_data_offset
, я получил ошибку в Chrome в виде: «MSE не поддерживает base_data_offset».В соответствии со спецификацией ИСО / МЭК 14996-10:
Если не указано иное, смещение базовых данных для первой дорожки в фрагменте фильма представляет собой позицию первого байта вмещающего блока фрагмента фильма.и для второго и последующих фрагментов дорожки по умолчанию используется конец данных, определенных предыдущим фрагментом.
Эта формулировка заставляет меня поверить, что data_offset
в первом trun
атомедолжен быть равен размеру moof
атома, а data_offset
во втором trun
атоме должен быть 0
(0 байтов от конца данных, определенных предыдущим фрагментом).Однако, когда я попробовал это, я получил ошибку, что видеоданные не могут быть проанализированы. что привело к тому, что данные, которые можно было проанализировать, были длиной атома moof
плюс общая длина первой дорожки (как если бы базовое смещение было первым байтомmoof
коробка, такая же, как первая дорожка)