19

FFmpeg Bitstream Filters Documentationを注意深く読んだ後でも、それらが実際に何のためにあるのかまだわかりません。

ドキュメントには、フィルターについて次のように記載されています。

デコードを実行せずにビットストリーム レベルの変更を実行する

誰かが私にそれをさらに説明できますか? ユースケースは物事を非常に明確にします。また、明らかに異なるフィルターがあります。それらはどのように異なりますか?

4

1 に答える 1

48

例を挙げて説明しましょう。FFmpeg ビデオ デコーダーは通常、呼び出しごとに 1 つのビデオ フレームを avcodec_decode_video2 に変換することによって機能します。そのため、入力は「1 つの画像」に相当するビットストリーム データであると想定されます。ファイル (ディスクのバイトの配列) からイメージに移行するこの問題を少し考えてみましょう。

「生の」(別紙) H264 (.h264/.bin/.264 ファイル) の場合、個々の nal ユニット データ (sps/pps ヘッダー ビットストリームまたは cabac でエンコードされたフレーム データ) は、先頭の nal ユニットのシーケンスで連結されます。コード (00 00 01 XX) の間にあります。ここで、XX は最終的なユニット タイプです。(最終データ自体が 00 00 01 データを持たないようにするために、RBSP エスケープされます。) したがって、h264 フレーム パーサーは、開始コード マーカーでファイルを単純に切り取ることができます。それらは、00 00 01 で始まり、00 00 01 の次の出現を除外するまで、00 00 01 を含む連続するパケットを検索します。次に、nal ユニット タイプとスライス ヘッダーを解析して、各パケットが属するフレームを見つけ、nal のセットを返します。h264 デコーダへの入力として 1 フレームを構成するユニット。

ただし、.mp4 ファイルの H264 データは異なります。mp4 の場合のように、多重化形式に既に長さマーカーが含まれている場合、00 00 01 開始コードは冗長であると見なすことができると想像できます。したがって、フレームごとに 3 バイトを節約するために、00 00 01 プレフィックスを削除します。また、PPS/SPS を最初のフレームの前に追加するのではなく、ファイル ヘッダーに配置し、00 00 01 プレフィックスも見逃しています。したがって、これを h264 デコーダーに入力すると、すべての nal ユニットのプレフィックスが必要になりますが、機能しません。h264_mp4toannexb _ビットストリーム フィルターは、ファイル ヘッダーの抽出された部分で pps/sps を識別し (ffmpeg はこれを「追加データ」と呼びます)、これと個々のフレーム パケットの各 nal を開始コードで先頭に追加し、入力する前にそれらを連結して戻すことにより、これを修正します。 h264デコーダーで。

「パーサー」と「ビットストリーム フィルター」の間には非常に微妙な違いがあると感じるかもしれません。これは本当です。正式な定義は、パーサーが一連の入力データを取得し、データを破棄したりデータを追加したりせずにフレームに分割することだと思います。パーサーが行う唯一のことは、パケットの境界を変更することです。一方、ビットストリーム フィルターは実際にデータを変更することができます。この定義が完全に正しいかどうかはわかりませんが (たとえば、以下の vp9 を参照)、mp4toannexb がパーサーではなく BSF であるという概念上の理由です (00 00 01 プレフィックスが追加されるため)。

このような「ビットストリームの微調整」がデコーダーをシンプルかつ均一に保つのに役立つ他のケース:

  • mpeg4 (divx) b フレーム アンパッキング (IPB としてコード化された IBP のような B フレーム シーケンスを AVI で取得し、正しいタイムスタンプを取得するために、人々は、IBP / IPB が次のようにフレームにパックされる B フレーム パッキングのこの概念を思いつきました。I-(PB)-()つまり、3 番目のパケットは空で、2 番目のパケットには 2 つのフレームがあります。これは、デコード フェーズで P および B フレームに関連付けられたタイムスタンプが正しいことを意味します。また、1 つのパケットに対して 2 フレーム分の入力データがあることも意味します。これは、ffmpeg の 1 フレーム イン 1 フレーム アウトの概念に違反しているため、bsf を作成してパケットを 2 つに分割し、マーカーを削除しました。パケットには2つのフレームが含まれているため、パーサーではなくBSFであると述べています-デコーダーに入力する前に。実際には、これにより、フレームのマルチスレッドに関する困難な問題が解決されます。VP9 は同じこと (スーパーフレームと呼ばれる) を行いますが、パーサーでフレームを分割するため、パーサーと BSF の分割は常に理論的に完全であるとは限りません。おそらくVP9はBSFと呼ばれるべきです)
  • hevc mp4 から annexb への変換 (上記と同じ話ですが、hevc の場合)
  • aac adts から ascへの変換 (これは基本的に h264/hevc annexb 対 mp4 と同じですが、aac オーディオの場合)
于 2015-08-16T12:27:55.093 に答える