FFmpeg を使用した VP9 によるライブ エンコード
エンコード パラメータ
VP9 には、ライブ エンコードを最適化するためのさまざまなパラメータが用意されています。これらの一般的な原則については、ビットレート モードで説明します。
FFmpeg VP9 エンコードの例
次の表に、VP9 エンコードの ffmpeg
呼び出しの例のパラメータを示します。
パラメータ | 説明 |
---|---|
-quality realtime |
realtime は、ライブ配信や 5 を超える速度に不可欠です。 |
-speed 6 |
ライブ / リアルタイム エンコードには、速度 5 ~8 を使用する必要があります。数値が小さいほど(5 または 6 )、品質は高くなりますが、より多くの CPU 能力が必要になります。数値が大きいほど(7 または 8 )、品質は低下しますが、遅延の少ないユースケースや、モバイルなどの CPU パワーの低いデバイスでは管理しやすくなります。 |
-tile-columns 4 |
タイリングでは、動画が長方形の領域に分割されるため、エンコードとデコードのマルチスレッド処理が可能になります。タイルの数は常に 2 の累乗です。0 = 1 タイル、1 = 2、2 = 4、3 = 8、4 = 16、5 = 32。 |
-frame-parallel 1 |
並列復号可能性機能を有効にします。 |
-threads 8 |
使用するスレッドの最大数。 |
-static-thresh 0 |
モーション検出のしきい値。 |
-max-intra-rate 300 |
最大 i フレーム ビットレート(%) |
-deadline realtime |
-quality realtime の代替(以前の)バージョン |
-lag-in-frames 0 |
遅延するフレームの最大数 |
-qmin 4 -qmax 48 |
量子化器の最小値と最大値。ここで設定する値はあくまで提案であり、この値を調整すると、圧縮効率と引き換えに動画の品質を上げたり下げたりできます。 |
-row-mt 1 |
行マルチスレッディングを有効にします。タイル列として最大 2 倍のスレッドを使用できます。0 = オフ、1 = オン。 |
-error-resilient 1 |
エラー復元機能を有効にします。 |
エンコード パラメータの選択
以下の情報は、ライブ アダプティブ ビットレート ストリーミング(ABR)に固定ビットレート(CBR)エンコードを使用する場合のものです。この場合、各ターゲット レートはパケージャーのマニフェストで明示的に設定されます。これにより、クライアントの料金間の「切り替え」がより明確になります。ビットレートの柔軟性が高い場合や、エンコードがチャンク化されている場合は、可変ビットレート(VBR)エンコードと CQ モードも選択肢となります。Q モードでは、ライブ動画に必要なリアルタイム エンコードが困難になります。詳しくは、ビットレート モードをご覧ください。
VP9 の操作方法について詳しくは、VOD 設定に関する記事もご覧ください。ただし、CBR に重点を置くことを考慮してください。
ヒントとコツ
ライブ配信では、すべての処理が 1 倍の最小リアルタイム エンコード速度に制限されます(FFmpeg は進行状況に応じてエンコード速度をレポートします)。エンコード速度が 1 倍を下回ると、エンコード プロセスがライブ動画の入力に追いつかず、ユーザーはバッファリングを経験します。また、送信が中断されると、ライブ ブロードキャスト中にストリームが使用できなくなります(アーカイブは通常使用できます)。
エンコード パラメータの例
次の表は、Linux を実行するクアッドコア i5 3.6Ghz デスクトップで、さまざまなフレームサイズにおける 25 fps での CPU 使用率を示しています。
解決までの目標時間 | FFmpeg VP9 パラメータ | CPU / 速度(例) |
---|---|---|
3840x2160(2160p) | -r 30 -g 90 -s 3840x2160 -quality realtime -speed 5 -threads 16 -row-mt 1 -tile-columns 3 -frame-parallel 1 -qmin 4 -qmax 48 -b:v 7800k | ~ 88% 0.39 倍 |
2560x1440(1440p) | -r 30 -g 90 -s 2560x1440 -quality realtime -speed 5 -threads 16 -row-mt 1 -tile-columns 3 -frame-parallel 1 -qmin 4 -qmax 48 -b:v 6000k | 約 86% 0.68 倍 |
1920x1080(1080p) | -r 30 -g 90 -s 1920x1080 -quality realtime -speed 5 -threads 8 -row-mt 1 -tile-columns 2 -frame-parallel 1 -qmin 4 -qmax 48 -b:v 4500k | ~ 82% 1.04 倍 |
1280x720(720p) | -r 30 -g 90 -s 1280x720 -quality realtime -speed 5 -threads 8 -row-mt 1 -tile-columns 2 -frame-parallel 1 -qmin 4 -qmax 48 -b:v 3000k | ~ 78% 1.77 倍 |
854x480(480p) | -r 30 -g 90 -s 854x480 -quality realtime -speed 6 -threads 4 -row-mt 1 -tile-columns 1 -frame-parallel 1 -qmin 4 -qmax 48 -b:v 1800k | ~ 64% 3.51 倍 |
640x360(360p) | -r 30 -g 90 -s 640x360 -quality realtime -speed 7 -threads 4 -row-mt 1 -tile-columns 1 -frame-parallel 0 -qmin 4 -qmax 48 -b:v 730k | ~ 62% 5.27 倍 |
426x240(240p) | -r 30 -g 90 -s 426x240 -quality realtime -speed 8 -threads 2 -row-mt 1 -tile-columns 0 -frame-parallel 0 -qmin 4 -qmax 48 -b:v 365k | ~ 66% 8.27 倍 |
FFmpeg の例は次のようになります。
ffmpeg -stream_loop 100 -i /home/id3as/Videos/120s_tears_of_steel_1080p.webm \
-r 30 -g 90 -s 3840x2160 -quality realtime -speed 5 -threads 16 -row-mt 1 \
-tile-columns 3 -frame-parallel 1 -qmin 4 -qmax 48 -b:v 7800k -c:v libvpx-vp9 \
-b:a 128k -c:a libopus -f webm pipe1
ヒントとコツ
ここでは、FIFO パイプ(「pipe1」)に出力しています。FFmpeg コマンドを実行する前に、このパイプを作成する必要があります。これを行うには、作業ディレクトリで
mkfifo pipe1
コマンドを実行します。Shaka Packager を使用すると、指定されたストリームの入力ソースとしてそのパイプがリッスンされます。他のパッケージ モデルでは、別の方法が必要になる場合があります。-row-mt
コマンドが認識されるようにするには、https://www.ffmpeg.org/download.html から FFmpeg の最新の安定版(現在は 3.3.3)を使用します。
アダプティブ ビットレート セットの例
FFmpeg を実行するマシンの性能によっては、次のすべてのエンコードを同時に配信できない場合があります。そのため、利用可能なリソースとターゲット ユーザーに適したサブセットをリストから選択する必要があります。
FFmpeg の完全な ABR セット
理想的なシナリオでは、前のセクションで説明したエンコードの例を組み合わせて、すべてを同時に生成する単一のコマンドを作成します。
ffmpeg -stream_loop 100 -i lakes1080p.mp4 \
-y -r 25 -g 75 -s 3840x2160 -quality realtime -speed 5 -threads 8 \
-tile-columns 2 -frame-parallel 1 \
-b:v 7800k -c:v libvpx-vp9 -b:a 196k -c:a libopus -f webm pipe1 \
-y -r 25 -g 75 -s 2560x1440 -quality realtime -speed 5 -threads 8 \
-tile-columns 2 -frame-parallel 1 \
-b:v 6000k -c:v libvpx-vp9 -b:a 196k -c:a libopus -f webm pipe2 \
-y -r 25 -g 75 -s 1920x1080 -quality realtime -speed 5 -threads 4 \
-tile-columns 2 -frame-parallel 1 \
-b:v 4500k -c:v libvpx-vp9 -b:a 196k -c:a libopus -f webm pipe3 \
-y -r 25 -g 75 -s 1280x720 -quality realtime -speed 5 -threads 4 \
-tile-columns 2 -frame-parallel 1 \
-b:v 3000k -c:v libvpx-vp9 -b:a 196k -c:a libopus -f webm pipe4 \
-y -r 25 -g 75 -s 854x480 -quality realtime -speed 6 -threads 4 \
-tile-columns 2 -frame-parallel 1 \
-b:v 2000k -c:v libvpx-vp9 -b:a 196k -c:a libopus -f webm pipe5 \
-y -r 25 -g 75 -s 640x360 -quality realtime -speed 7 -threads 2 \
-tile-columns 1 -frame-parallel 0 \
-b:v 730k -c:v libvpx-vp9 -b:a 128k -c:a libopus -f webm pipe6 \
-y -r 25 -g 75 -s 426x240 -quality realtime -speed 8 -threads 2 \
-tile-columns 1 -frame-parallel 0 \
-b:v 365k -c:v libvpx-vp9 -b:a 64k -c:a libopus -f webm pipe7
ただし、上記のフルセットには、非常に強力な CPU が必要になります。また、一部のチップセットで提供されているようなハードウェア GPU オフロードのサポートが必要になる可能性もあります。Intel Kabylake(以降)には完全なハードウェア エンコード パイプラインがあります。(Kabylake GPU は 8 ビット VP9 エンコードはできますが、10 ビットはできません)。
Shaka Packager を使用した実用的なデスクトップの例
一般的なデスクトップ マシンのより実用的な例では、Shaka Packager を使用する場合があります。Shaka を設定する簡単な方法は、Google の DockerHub イメージを使用して、Docker コンテナ内にインストールすることです。手順については、こちらをご覧ください。
https://github.com/google/shaka-packager#using-docker-for-testing--development
この例では、次の構成のマシンを使用しました。
システム | ホスト: obs カーネル: 4.4.0-91-lowlatency x86_64(64 ビット) |
パソコン | Xfce 4.12.3 ディストリビューション: OS: https://ubuntustudio.org/2016/10/ubuntu-studio-16-10-released/ |
CPU | クアッドコア Intel Core i5-6500(-MCP-) キャッシュ: 6144 KB クロック速度: 最大: 3600 MHz 1: 800 MHz 2: 800 MHz 3: 800 MHz 4: 800 MHz |
グラフィック カード | Intel Skylake 統合グラフィックス |
メモリ | 8 GB RAM |
実際には、このマシンは次の使用可能な範囲の ABR エンコードを最適に生成できます。FFmpeg は常に 1 倍のエンコード速度を報告します。
ffmpeg -stream_loop 100 -i 120s_tears_of_steel_1080p.webm \
-y -r 30 -g 90 -s 1920x1080 -quality realtime -speed 7 -threads 8 \
-row-mt 1 -tile-columns 2 -frame-parallel 1 -qmin 4 -qmax 48 \
-b:v 4500k -c:v libvpx-vp9 -b:a 128k -c:a libopus -f webm pipe1 \
-y -r 30 -g 90 -s 1280x720 -quality realtime -speed 8 -threads 6 \
-row-mt 1 -tile-columns 2 -frame-parallel 1 -qmin 4 -qmax 48 \
-b:v 3000k -c:v libvpx-vp9 -b:a 128k -c:a libopus -f webm pipe2 \
-y -r 30 -g 90 -s 640x360 -quality realtime -speed 8 -threads 2 \
-row-mt 1 -tile-columns 1 -frame-parallel 1 -qmin 4 -qmax 48 \
-b:v 730k -c:v libvpx-vp9 -b:a 128k -c:a libopus -f webm pipe3
-speed
の設定がかなり高いことに注意してください。これらの設定は試験的に確立されたものであり、マシンによって異なります。
Shaka Packager のオーバーヘッド
パッケージングは、特に CPU 使用率の高いアクティビティではありません。FFmpeg によってサブセットのみが配信されている場合でも、すべての出力をリッスンするように Shaka Packager を設定できます。上記のマシンでテストされたパッケージャーの設定は次のとおりです。
packager \
in=pipe1,stream=audio,init_segment=livehd-audio-1080.webm,segment_template=livehd-audio-1080-\$Number\$.webm \
in=pipe1,stream=video,init_segment=livehd-video-1080.webm,template=livehd-video-1080-\$Number\$.webm \
in=pipe2,stream=audio,init_segment=livehd-audio-720.webm,segment_template=livehd-audio-720-\$Number\$.webm \
in=pipe2,stream=video,init_segment=livehd-video-720.webm,template=livehd-video-720-\$Number\$.webm \
in=pipe3,stream=audio,init_segment=livehd-audio-360.webm,segment_template=livehd-audio-360-\$Number\$.webm \
in=pipe3,stream=video,init_segment=livehd-video-360.webm,template=livehd-video-360-\$Number\$.webm \
--mpd_output livehd.mpd --dump_stream_info --min_buffer_time=10 --time_shift_buffer_depth=300 \
--segment_duration=3 --io_block_size 65536