MTZ_AUF for エッジレベル調整 [高速化]
エッジレベル調整はがらくたハウスのがらくた置き場で公開してくださっているAviutlのフィルタ。
エッジ調整の効果がすごくいい、素晴らしいフィルタなのだけど、わりと重い。
作者様によると、これはどうも並列化されてないことが原因の一つらしい。3級以下のFlash置き場 - えっじれべるちょうせい
というわけで強引に高速化してみる、そういう話。
※素直に並列化 + 拡張命令の使用でこの方法よりも安定・さらに高速化したエッジレベル調整MT 0.7 v7をこちらで公開していますので、どうぞ。
テストした環境について
基本的な環境
Win7 x64 SP1
Core i5 2500 @ 3.8GHz (4C/4T)
RAM 4GB DDR3-1333
ソース
ts(MPEG2) 1920x1080i 29.97fps
出力
1920x1080p 自動フィールドシフト 23.976fps 180秒
Aviutl環境
Aviutl 0.99k2
MPEG-2 VIDEO VFAPI Plug-In 0.7.5a
x264guiEx 1.33
x264 x64 r2164+649 8bit
--preset slow --crf 21.5 --ipratio 1.5 --qpstep 12 --qcomp 0.7 --no-mbtree --vbv-bufsize 17500 --vbv-maxrate 17500 --aq-strength 0.4 --psy-rd 1:0.2 --scenecut 50 --keyint 300 --min-keyint 4 --subme 9 --ref 4 --no-fast-pskip --no-dct-decimate --trellis 2 --colormatrix bt709 --level 4
重くもなく、かといって軽くもない、そんな設定。
Aviutlフィルタ
自動フィールドシフト
透過性ロゴ
クリッピング
色域変換
PMD_MT
リサイズフィルタ(Spline36)
エッジレベル調整
バンディング低減
エッジレベル調整を使うとCPUが遊ぶ
エッジレベル調整を使うと、CPU使用率が上がらなくなり、エンコ速度がでない…なんて問題が起こる。例えば、4コアのCore i5 2500だと、CPU使用率が平均約70%ほどとなって、かなりCPUが遊んでしまっている。
x264はオプションによっても異なるがかなり並列度は高い。なので、CPUが遊んでしまう場合、x264の前の段階で詰まってることが原因なことが多い。今回はエッジレベル調整が律速になってしまっている。
こういう場合、高速化の手段としては単純にAviutlを2つ起動して、2つ同時にエンコードするという手がある。
これは簡単だけれども、いろいろ使い勝手が悪い。2つエンコードするものがないときには使えないし、メモリも喰う(まあ最近はメモリ安いから、足りなければ買ってくればいいわけで、これはどうでもいいかな?)。そもそも2つのエンコードが2時間で終わるよりは、1つのエンコードが1時間ちょいで終わってくれたほうが個人的にはありがたい。
というわけで1つのAviutlでCPUの力を使い切って高速化したい。
フレーム分割による並列化(MTZ_AUFを使用する)
シングルスレッドのフィルタを並列化するために、YOUMEI様が「AviUtlのAUFプラグインを複数スレッド化するAUF (MTZ_AUF)」を公開してくださっている。ありがとうございます、素晴らしいです。
仕組みとしては、フレームをスレッド数だけ分割して、別スレッドで処理させる、というもの。
図は2スレッドの場合。
しかし、readmeには、
上下のピクセルが重要な意味を持つプラグインには適用しない方が無難です。たとえば画面の中央付近に問題(フィルタ適用ミス)などが発生する可能性があります。
とあって、分割境界付近の処理がおかしくなるかもしれないよ、とのことだ。
そして、エッジレベル調整がまさにこれで、mtz_aufを適用すると、こんな感じで分割境界にフィルタがかかっていない領域ができる。
エッジレベル調整を限界まで強くかけて、わかりやすくした例。
画面中央付近に横一線にエッジレベル調整のかかっていない帯が見える。フレームを分割した境界付近でエッジレベル調整がうまくかからなかったようだ。幅は6ピクセルぐらい?
オーバーラップさせて処理する
これをなんとかするには、フレームを分割するときに少しオーバーラップさせて処理をして、最終的に重複させた部分(境界のうまくフィルタがかからない部分)付近は捨ててしまえばいい。こんな感じ。
こんな感じでちょっと重複して処理をして、重複させた部分は最後に捨ててしまおう、という考え。
MTZ_AUFはソースを公開していただけているので、ちょこちょこ改造してオーバーラップ処理ができるようにしてみた。
この方法の問題点は、スレッド分割をすればするほど、2重に計算する領域が増えて、計算量が増えるということ。具体的には(スレッド数-1)×オーバーップ高さ×2×フレーム幅 分だけ2重に計算することになる。
つまり、並列化による高速化 > (増える計算量 + 同期待ちなどの並列化によるコスト) とならなければ、CPU使用率は上がっても速度は落ちてしまう。
どうなるのか、こればっかりはやってみないとわからない…のでやってみた。
で、とりあえず、これが今回作った改造版での画像の結果。
エッジレベル調整がかかってないせいでできてた線がきれいに消えてる。
さっきの画像とタブで開いて、切り替えてみるとわかりやすいかも。
とりあえず、この方法で「境界付近でフィルタがうまくかからない」問題は解決した。
次は問題の速度とかを見てみる。
並列化なし時の様子
CPUは結構遊んでいる…
並列化なしの時のスレッドの様子
こんな感じで、TID(ThreadID)=3372のスレッドがやたら仕事してるけど、これがAviutlのシングル用スレッドで、エッジレベル調整がここで動いてるんじゃないかなあ…と予想できる。
2スレッド並列時の様子
次に、エッジレベル調整を今回作ったMTZ_AUF改造版で2スレッド並列にしてみる。
2スレッドの時
CPU使用率が少し上がった。まだ遊んでるけど。もっと働けい!
2スレッド並列の時のスレッドの様子
TID=2208,4060というスレッドが出来て、エッジレベル調整が並列で動いている。
3スレッド並列時の様子
十分仕事してる。
スレッドの様子>>
4スレッド並列時の様子
こちらも同様。
スレッドの様子>>
速度の比較
さっきも書いたように、今回の方法ではCPU使用率が上がっても、オーバーラップして計算させることで増えた計算によって遅くなる可能性がある。なので実際に速度を比較。
やはりエッジレベル調整は重いようで、(効率はさておくとしても、)順調に高速化している。
もっとも、効率も悪くない。CPU使用率70%前後→100%で40%弱の高速化なので、結構いいほうじゃないかと。
ただ、Core i7みたいな論理8コアの場合にthreads=8まで順調に高速化するとはとても思えない。どうなるかわからないけど、物理コアは4だし、4以上にしても計算量が増えるせいで逆に遅くなるんじゃないかな…
安定性は?
avisynthでもMT("")とかいう謎のものがあって、同じように並列化ができる。で、2年ぐらい前遊んでみたんだけど…ものすごく不安定だった。エンコ開始時とかでもなく、エンコ途中で落ちて、さすがに手に負えなかった。
avsスクリプト書いたり、バッチファイルを書いたりするのが個人的にあまり楽しくなかったので最近avisynthはあまり触ってないけど、最近はどうなんだろうか。MTは諦めて、フィルタ内部で並列化してもらうのか。それともプロセス2つ走らせるのかな…。
とりあえず、今回のMTZ_AUF for エッジレベル調整はエッジレベル調整を対象とする限り安定して動きます。そのはずです…
MTZ_AUF for エッジレベル調整
今回、YOUMEI様に改造版の公開の許可を頂きました。ありがとうございます。
[動作環境]
Windows XP (x86)
Vista,7 (x86/x64)
Aviutl 0.99g4 以降
マルチコアCPU / SSE2に対応したCPU
エッジレベル調整用
[注意事項]
無保証です。自己責任で使用してください。
mtz_auf for エッジレベル調整を使用したことによる、いかなる損害・トラブルについても責任を負いません。
また、基本的にエッジレベル調整専用です。他のAviutlフィルタへ適用した場合は、おかしくなる可能性が高いです。
なんかおかしな点などありましたら、コメント欄にどうぞ。
[使用方法]
オリジナルのものと少し異なります。
1. mtz_auf.aufをAviUtl.exeと同じフォルダ、あるいはpluginフォルダに放り込みます。
2. edgelevelMT.aufを、並列化したいスレッド数だけコピーし、そのファイルの拡張子をそれぞれ「.mt0」、「.mt1」、…のようにします。
3. mtz_auf.aufの名前を変更し、edgelevelMT.aufとします。
4. mtz_auf.iniの名前を変更し、edgelevelMT_mtz.iniとします。このファイルを開き、値を編集します。
overwrapが(縦方向に)オーバーラップ処理する画素数、
threadsがスレッド数です。
エッジレベル調整ではoverwrapは4ぐらいがいいと思います。(少なくとも、これ以上にする必要はない)
5. Aviutlのファイル > システムの設定で、高さを (スレッド数-1)×オーバーラップ量×2 だけ増やしてください。
例えば、高さ1080を編集し、スレッド数4、オーバーラップ量4なら、1080 + (4-1)×4×2で1104、またはそれ以上に設定してください。
これを忘れて高さが不足した場合、メッセージが出るようになっています。
6. AviUtlを再起動します。
Aviutlが問題なく起動し、edgelevelMT.aufが無事に動作していること(設定ウインドウが表示される…など)を確認してください。
4スレッドの時の例
[pluginフォルダ]
edgelevelMT.auf
mtz_auf.auf
mtz_auf.ini
↓
[pluginフォルダ]
edgelevelMT.mt0 ← 元は edgelevelMT.auf
edgelevelMT.mt1 ← 元は edgelevelMT.auf
…
edgelevelMT.mt3 ← 元は edgelevelMT.auf
edgelevelMT.auf ← 元は mtz_auf.auf
edgelevelMT_mtz.ini ← 元は mtz_auf.ini
クリックで拡大
さらにedgelevelMT_mtz.iniのthreadsを4に設定する。
[MTZ_AUF]
threads=4
overwrap=4
設定すべきスレッド数
スレッド数は2~32の範囲で、iniファイルのthreadsで設定できます。反映にはAviutlの再起動が必要です。32まで設定できますが、絶対必要ありません。
オーバーラップして計算するため、スレッド分割をすればするほど重複する演算が多くなります。
なので、増やしすぎるとCPU使用率は上がっても、逆に遅くなる可能性があります。
CPUの性能、Aviutlで使用するフィルタの重さ、x264のオプションなどによって最適なスレッド数は変わります。
需要あんのかな…
まあ、こんなことしなくてもAviutl2つ走らせればいいだろ…と言われそうだ。
※素直に並列化 + 拡張命令の使用でこの方法よりも安定・さらに高速化したエッジレベル調整MT 0.7 v7をこちらで公開していますので、どうぞ。
ダウンロード>>
MTZ_AUF.auf、エッジレベル調整を公開してくださっている作者様に御礼申し上げます。
YOUMEI様
http://www2u.biglobe.ne.jp/~youmei/
がらくたハウスのがらくた置き場
http://www.geocities.jp/flash3kyuu/
長くなりました。お疲れ様です。
エッジ調整の効果がすごくいい、素晴らしいフィルタなのだけど、わりと重い。
作者様によると、これはどうも並列化されてないことが原因の一つらしい。3級以下のFlash置き場 - えっじれべるちょうせい
というわけで強引に高速化してみる、そういう話。
※素直に並列化 + 拡張命令の使用でこの方法よりも安定・さらに高速化したエッジレベル調整MT 0.7 v7をこちらで公開していますので、どうぞ。
テストした環境について
基本的な環境
Win7 x64 SP1
Core i5 2500 @ 3.8GHz (4C/4T)
RAM 4GB DDR3-1333
ソース
ts(MPEG2) 1920x1080i 29.97fps
出力
1920x1080p 自動フィールドシフト 23.976fps 180秒
Aviutl環境
Aviutl 0.99k2
MPEG-2 VIDEO VFAPI Plug-In 0.7.5a
x264guiEx 1.33
x264 x64 r2164+649 8bit
--preset slow --crf 21.5 --ipratio 1.5 --qpstep 12 --qcomp 0.7 --no-mbtree --vbv-bufsize 17500 --vbv-maxrate 17500 --aq-strength 0.4 --psy-rd 1:0.2 --scenecut 50 --keyint 300 --min-keyint 4 --subme 9 --ref 4 --no-fast-pskip --no-dct-decimate --trellis 2 --colormatrix bt709 --level 4
重くもなく、かといって軽くもない、そんな設定。
Aviutlフィルタ
自動フィールドシフト
透過性ロゴ
クリッピング
色域変換
PMD_MT
リサイズフィルタ(Spline36)
エッジレベル調整
バンディング低減
エッジレベル調整を使うとCPUが遊ぶ
エッジレベル調整を使うと、CPU使用率が上がらなくなり、エンコ速度がでない…なんて問題が起こる。例えば、4コアのCore i5 2500だと、CPU使用率が平均約70%ほどとなって、かなりCPUが遊んでしまっている。
x264はオプションによっても異なるがかなり並列度は高い。なので、CPUが遊んでしまう場合、x264の前の段階で詰まってることが原因なことが多い。今回はエッジレベル調整が律速になってしまっている。
こういう場合、高速化の手段としては単純にAviutlを2つ起動して、2つ同時にエンコードするという手がある。
これは簡単だけれども、いろいろ使い勝手が悪い。2つエンコードするものがないときには使えないし、メモリも喰う(まあ最近はメモリ安いから、足りなければ買ってくればいいわけで、これはどうでもいいかな?)。そもそも2つのエンコードが2時間で終わるよりは、1つのエンコードが1時間ちょいで終わってくれたほうが個人的にはありがたい。
というわけで1つのAviutlでCPUの力を使い切って高速化したい。
フレーム分割による並列化(MTZ_AUFを使用する)
シングルスレッドのフィルタを並列化するために、YOUMEI様が「AviUtlのAUFプラグインを複数スレッド化するAUF (MTZ_AUF)」を公開してくださっている。ありがとうございます、素晴らしいです。
仕組みとしては、フレームをスレッド数だけ分割して、別スレッドで処理させる、というもの。
図は2スレッドの場合。
しかし、readmeには、
上下のピクセルが重要な意味を持つプラグインには適用しない方が無難です。たとえば画面の中央付近に問題(フィルタ適用ミス)などが発生する可能性があります。
とあって、分割境界付近の処理がおかしくなるかもしれないよ、とのことだ。
そして、エッジレベル調整がまさにこれで、mtz_aufを適用すると、こんな感じで分割境界にフィルタがかかっていない領域ができる。
エッジレベル調整を限界まで強くかけて、わかりやすくした例。
画面中央付近に横一線にエッジレベル調整のかかっていない帯が見える。フレームを分割した境界付近でエッジレベル調整がうまくかからなかったようだ。幅は6ピクセルぐらい?
オーバーラップさせて処理する
これをなんとかするには、フレームを分割するときに少しオーバーラップさせて処理をして、最終的に重複させた部分(境界のうまくフィルタがかからない部分)付近は捨ててしまえばいい。こんな感じ。
こんな感じでちょっと重複して処理をして、重複させた部分は最後に捨ててしまおう、という考え。
MTZ_AUFはソースを公開していただけているので、ちょこちょこ改造してオーバーラップ処理ができるようにしてみた。
この方法の問題点は、スレッド分割をすればするほど、2重に計算する領域が増えて、計算量が増えるということ。具体的には(スレッド数-1)×オーバーップ高さ×2×フレーム幅 分だけ2重に計算することになる。
つまり、並列化による高速化 > (増える計算量 + 同期待ちなどの並列化によるコスト) とならなければ、CPU使用率は上がっても速度は落ちてしまう。
どうなるのか、こればっかりはやってみないとわからない…のでやってみた。
で、とりあえず、これが今回作った改造版での画像の結果。
エッジレベル調整がかかってないせいでできてた線がきれいに消えてる。
さっきの画像とタブで開いて、切り替えてみるとわかりやすいかも。
とりあえず、この方法で「境界付近でフィルタがうまくかからない」問題は解決した。
次は問題の速度とかを見てみる。
並列化なし時の様子
CPUは結構遊んでいる…
並列化なしの時のスレッドの様子
こんな感じで、TID(ThreadID)=3372のスレッドがやたら仕事してるけど、これがAviutlのシングル用スレッドで、エッジレベル調整がここで動いてるんじゃないかなあ…と予想できる。
2スレッド並列時の様子
次に、エッジレベル調整を今回作ったMTZ_AUF改造版で2スレッド並列にしてみる。
2スレッドの時
CPU使用率が少し上がった。まだ遊んでるけど。もっと働けい!
2スレッド並列の時のスレッドの様子
TID=2208,4060というスレッドが出来て、エッジレベル調整が並列で動いている。
3スレッド並列時の様子
十分仕事してる。
スレッドの様子>>
4スレッド並列時の様子
こちらも同様。
スレッドの様子>>
速度の比較
さっきも書いたように、今回の方法ではCPU使用率が上がっても、オーバーラップして計算させることで増えた計算によって遅くなる可能性がある。なので実際に速度を比較。
やはりエッジレベル調整は重いようで、(効率はさておくとしても、)順調に高速化している。
もっとも、効率も悪くない。CPU使用率70%前後→100%で40%弱の高速化なので、結構いいほうじゃないかと。
ただ、Core i7みたいな論理8コアの場合にthreads=8まで順調に高速化するとはとても思えない。どうなるかわからないけど、物理コアは4だし、4以上にしても計算量が増えるせいで逆に遅くなるんじゃないかな…
安定性は?
avisynthでもMT("")とかいう謎のものがあって、同じように並列化ができる。で、2年ぐらい前遊んでみたんだけど…ものすごく不安定だった。エンコ開始時とかでもなく、エンコ途中で落ちて、さすがに手に負えなかった。
avsスクリプト書いたり、バッチファイルを書いたりするのが個人的にあまり楽しくなかったので最近avisynthはあまり触ってないけど、最近はどうなんだろうか。MTは諦めて、フィルタ内部で並列化してもらうのか。それともプロセス2つ走らせるのかな…。
とりあえず、今回のMTZ_AUF for エッジレベル調整はエッジレベル調整を対象とする限り安定して動きます。そのはずです…
MTZ_AUF for エッジレベル調整
今回、YOUMEI様に改造版の公開の許可を頂きました。ありがとうございます。
[動作環境]
Windows XP (x86)
Vista,7 (x86/x64)
Aviutl 0.99g4 以降
マルチコアCPU / SSE2に対応したCPU
エッジレベル調整用
[注意事項]
無保証です。自己責任で使用してください。
mtz_auf for エッジレベル調整を使用したことによる、いかなる損害・トラブルについても責任を負いません。
また、基本的にエッジレベル調整専用です。他のAviutlフィルタへ適用した場合は、おかしくなる可能性が高いです。
なんかおかしな点などありましたら、コメント欄にどうぞ。
[使用方法]
オリジナルのものと少し異なります。
1. mtz_auf.aufをAviUtl.exeと同じフォルダ、あるいはpluginフォルダに放り込みます。
2. edgelevelMT.aufを、並列化したいスレッド数だけコピーし、そのファイルの拡張子をそれぞれ「.mt0」、「.mt1」、…のようにします。
3. mtz_auf.aufの名前を変更し、edgelevelMT.aufとします。
4. mtz_auf.iniの名前を変更し、edgelevelMT_mtz.iniとします。このファイルを開き、値を編集します。
overwrapが(縦方向に)オーバーラップ処理する画素数、
threadsがスレッド数です。
エッジレベル調整ではoverwrapは4ぐらいがいいと思います。(少なくとも、これ以上にする必要はない)
5. Aviutlのファイル > システムの設定で、高さを (スレッド数-1)×オーバーラップ量×2 だけ増やしてください。
例えば、高さ1080を編集し、スレッド数4、オーバーラップ量4なら、1080 + (4-1)×4×2で1104、またはそれ以上に設定してください。
これを忘れて高さが不足した場合、メッセージが出るようになっています。
6. AviUtlを再起動します。
Aviutlが問題なく起動し、edgelevelMT.aufが無事に動作していること(設定ウインドウが表示される…など)を確認してください。
4スレッドの時の例
[pluginフォルダ]
edgelevelMT.auf
mtz_auf.auf
mtz_auf.ini
↓
[pluginフォルダ]
edgelevelMT.mt0 ← 元は edgelevelMT.auf
edgelevelMT.mt1 ← 元は edgelevelMT.auf
…
edgelevelMT.mt3 ← 元は edgelevelMT.auf
edgelevelMT.auf ← 元は mtz_auf.auf
edgelevelMT_mtz.ini ← 元は mtz_auf.ini
クリックで拡大
さらにedgelevelMT_mtz.iniのthreadsを4に設定する。
[MTZ_AUF]
threads=4
overwrap=4
設定すべきスレッド数
スレッド数は2~32の範囲で、iniファイルのthreadsで設定できます。反映にはAviutlの再起動が必要です。32まで設定できますが、絶対必要ありません。
オーバーラップして計算するため、スレッド分割をすればするほど重複する演算が多くなります。
なので、増やしすぎるとCPU使用率は上がっても、逆に遅くなる可能性があります。
CPUの性能、Aviutlで使用するフィルタの重さ、x264のオプションなどによって最適なスレッド数は変わります。
需要あんのかな…
まあ、こんなことしなくてもAviutl2つ走らせればいいだろ…と言われそうだ。
※素直に並列化 + 拡張命令の使用でこの方法よりも安定・さらに高速化したエッジレベル調整MT 0.7 v7をこちらで公開していますので、どうぞ。
ダウンロード>>
MTZ_AUF.auf、エッジレベル調整を公開してくださっている作者様に御礼申し上げます。
YOUMEI様
http://www2u.biglobe.ne.jp/~youmei/
がらくたハウスのがらくた置き場
http://www.geocities.jp/flash3kyuu/
長くなりました。お疲れ様です。