Aviutl GPUフィルタ(OpenCL版) clfilters

GWの前半は、x264guiEx 3.00の導入方法を紹介する動画を作っていたのだけど、GWの後半の時間で、以前要望いただいた各GPUフィルタのAviutl版を作った。

ひとつのフィルタの中に、複数のGPUフィルタを含んでいて、これらを一括して使えるようになっている。

以前、同じようなNVEncのCUDA実装をAviutlに移植したCUDA フィルタを作成したことがあったのだけど、CUDAだと(当然)NVIDIA GPUでしか使用できないというのが難点。

そこで今回は、Intel / NVIDIA / AMD のいずれのGPUでも使用できるようにQSVEnc/VCEEncのOpenCL実装をAviutlに移植したOpenCLフィルタにしてみた。





対応しているフィルタはいまのところ11種類で、適用順は固定で下記の通り。

- 色空間変換
- nnedi
- ノイズ除去(knn)
- ノイズ除去(pmd)
- ノイズ除去(smooth)
- リサイズ
- unsharp
- エッジレベル調整
- warpsharp
- バンディング低減
- 色調補正

将来的には適用順を変更できるようにしたいところ。

また、現状時間方向に参照が必要なフィルタ(3Dフィルタ)には対応できていない。ちょっとどう実装したらよいかわかっていないので、当面は非対応の予定。



QSVEnc / NVEnc / VCEEnc フィルタとの違い



基本的には、QSVEnc / NVEnc / VCEEncのVppフィルタをほぼそのまま移植したものなの。ただ、QSVEnc / NVEnc / VCEEncでは速度重視なので、出力色空間に応じてなるべく軽い色フォーマットで処理している。(YUV420 8bit/16bitが多いと思う)。

一方、今回作成したAviutl版は、一貫してYUV444 16bitで処理するので、特に色差成分について少し結果が違いそう。(そう大きな差ではないはずなので確認用としては十分だとは思う)



ダウンロード>>

clfiltersの詳細



処理概要



Aviutlの内部フォーマット(YC48)からGPUで扱いやすいYUV444 16bitに変換てから、GPUに転送してフィルタ処理を行う。その後、処理結果をCPUに転送し、YC48に戻して処理を完了させている。

YC48 → YUV444 16bit → GPUに転送 → VppフィルタをGPUで連続処理 → CPUに転送 → YUV444 16bit → YC48



GPUフィルタの高速化



以前のCUDA版ではcufiltersでは行っていなかった最適化を真面目に行った。

GPUフィルタの課題

GPUで高速にフィルタ処理ができたとしても、残念ながらGPUフィルタが高速とは限らない。

- CPU-GPU間転送が遅い
Aviutlでは基本的にはフレームのデータがCPUにあるため、GPUフィルタを適用する場合、CPU-GPU間の転送が往復で必要になる。ところがこれはかなり遅い処理で、転送開始のレイテンシも大きいし、転送にも時間がかかる。

- そもそもGPUでの計算開始が遅い。
すぐに計算を行ってくれるCPUと異なり、GPUに計算を発行してから実際に開始されるまでにそれなりの遅延がある。

CPU-GPU間転送や、GPUの処理開始遅延の影響で、計算を直列に並べると、フィルタによっては普通にCPU版をAVX2とかで最適化したほうが高速ということになってしまう。GPU版を高速にするためには、

- CPU-GPU間転送を減らす
- CPU-GPU間転送やGPU計算を並行して実行する

などの対策が必要になる。



実施済みの最適化



いくつかの最適化に段階的に取り組んでみた。

初期版: CPU-GPU間転送を減らす

複数のGPUフィルタを一度に適用することで、CPU-GPU間転送を削減。GPUフィルタをひとつひとつ適用するのに比べ、転送回数を減らすのが狙い。

初期版: 内蔵GPU使用時のCPU-GPU間転送の削減

Intel GPUなど、内蔵GPUを使用する場合、OpenCLのAPIを適切に使うことでCPU-GPU間転送をなくすようにした (いわゆるZero Copy)。

最適化1: CPU-GPU間転送とGPU計算を並行して実行

保存時にはフレームを先読みすることで、CPU-GPU間転送とGPU計算を並行して行うことで、CPU-GPU間転送や処理開始の遅延を抑制した。(実装の単純化のため、保存時のみ行っており、編集時は行っていない。)

最適化2: メモリ確保・解放の削減 (NVIDIA)

もともとのOpenCL実装はIntel/AMD GPU向けで、これらのGPUでは cl_khr_image2d_from_buffer というOpenCL拡張が問題なく使えたので、これを前提にした最適化をしてしまっていた。

一方、NVIDIAはこの拡張には対応していないようで(CUDAでは似たようなことできるのに何で?)、この拡張を使わずに動作させるために、メモリ確保・コピー・解放を毎フレーム行ってしまっていた。GPUのメモリ確保・解放はかなり遅いので、メモリを使いまわすようにしてメモリ確保・解放をなるべくしないようにした。

最適化3: さらなるメモリ確保・解放の削減

意図せずメモリ確保・解放を連発していた個所が残っていたので修正。

最適化4: 不要な同期の削除

まだGPUが遊んでいる時間が多い状況だったので、VTuneなどを使って、OpenCL APIの呼ばれ方などをチェック。OpenCLリソースの解放漏れにより、無駄な同期がかかってしまっているようだったので、これを解消して高速化。



保存時の処理速度



実際にベンチマークプラグインを使って処理速度を測定してみた。

入力
sakura_op.mpg 1280x720 30fps 3501frame

環境
Win11 x64
Aviutl 1.10
Intel i9 12900K + Intel iGPU HDG770
NVIDIA GeForce RTX2070

有効フィルタ (3つ)
pmd_mt 回数:2, 強さ:100, 閾値:100
リサイズ 1280x720→1920x1080 spline36
エッジレベル調整 強さ:5, 閾値:20, 黒:0, 白:0



え~と、CPUのほうが速くね...? 悲しみ。

まあ、それはおいといて、最適化1~4によってだいぶ高速化できていて、特にRTX2070では最初の実装から比べると3.3倍速くすることができた。GPUではこうした細かな最適化の効果が大きいようで、やはりGPUフィルタではいろいろチェックすべきことが多そう。

ただ、そうは言っても、現状でも最適化されたCPUフィルタよりは遅くなってしまっている。やはりCPU-GPU間の転送や色フォーマットの変換など、GPUフィルタ特有のオーバーヘッドがいろいろ載ってくるため、今回試したような比較的軽量なフィルタではAVX2等で最適化CPUフィルタのほうが高速、ということになってしまった。

もちろん、現時点で最新のCPUのi9 12900Kと、1世代前のGPUのRTX2070での戦いなので、CPUとGPUの性能比によっては逆転することもありそうだし、もっと重いフィルタ(nnediやsmooth)を使えば、GPUのほうが有利になっていくとは思う。

また、今回はベンチマークプラグインで計測したので、デコードとフィルタだけがぶん回っている状況だけど、本来はエンコードも行うことになると思う。なので、GPUフィルタがCPUより遅いから無意味ということはなくて、CPUでの演算をGPUに移すことで、CPUがエンコードに回せる時間が増えるといったメリットもあるかもしれない。

# まあもともとはGPUフィルタの効果の確認用なので、このぐらい出ていれば十分?
スポンサーサイト



コメントの投稿

非公開コメント

No title

ありがとうございます。
これでいろいろ作業が捗ります。

openclが利用できないとの表示

管理人さん、こんにちは。
今回、こちらのGPUフィルタを試させていただこうと、ダウンロードした後aviutlのプラグインフォルダに入れてみたのですが、『デバイス選択』の箇所に使用しているGPU名が表示されず、動画を読み込んでみても『openclを使用できません』的なメッセージが表示されてしまいます。
なので、PCがこちらのGPUフィルタの必要条件を満たしていないと思われますが、何が足らないのかが分かりません。

GPUは1050Tiでドライバは最新版の1つ前の473.04です。
なお、PCは動画編集専用に割り切って使っている物で、OSは推奨動作環境外となるWindows7です。
(セキュリティが心配なのでネットには繋げてません)

お手数ですが、アドバイスをお願いします。


Re: openclが利用できないとの表示

まずはじめに、Windows7は想定動作環境ではなく、動作確認も一切していないため、申し訳ありませんがもともと動かないかもしれないです…。

「openclを使用できません」は、OpenCL初期化の失敗やOpenCL経由でのGPUの認識に失敗したことによるものです。OpenCLが適切に導入されていないか、clfiltersの認識方法の問題か、どちらかと思われます。


OpenCLの認識状況の確認
最近のGPU-Zでは、[Advanced]タブで[OpenCL]を選択するとOpenCL環境の情報を確認できます。お使いの環境で適切に表示されているかご確認ください。

表示が適切になされない場合は、基本的には環境依存の問題で、GPUドライバの再インストールなどで改善する可能性があります。


clfitlersでの認識状況の確認
GPU-Zのほうでは問題なくOpenCLの表示がある場合は、clfitlersでの認識の問題と思われます。こちらの詳細については、

1. Aviutlを起動する
2. clfiltersの[ログ出力]を「debug」にし、[ファイル出力]にチェックを入れる
3. 動画ファイルを読み込んで、clfiltersを有効にする

とすると、Aviutl.exeと同じフォルダにclfilters.auf.log というファイルができると思います。

※この後ログの設定をquietに戻し、[ファイル出力]のチェックも外しておいてください。

このclfilters.auf.logの内容をすべてコピペいただけると、もう少し詳しくわかるかもしれません。

続・openclが利用できないとの表示

管理人さん、お世話になっております

GPU-Zを使いましてopenclの状態を確認したところ『not supported』と表示されたので、現時点ではopenclが使用できる状態でないようです。
opencl.dll、opencl64.dllなどがcドライブ内に有るのは確認していたので、この結果には正直驚きましたが、使える状態でないと云うのなら足りないものをインストールすれば事態は改善するのではと気持ちを切り替えました。
ただ、いざ調べてみると開発元だけでなくintelやNVIDIAが自社でopenclを公開していてどれをインストールすればよいか分からず、とりあえずNVIDIA社のGPUなのだからとCUDA Toolkit(これをインストールすればopenclもインストールされるそうなので)を導入し、グラフィックカードのドライバも最新版にしましたが、今のところ事態は改善されておりません。

引き続き対策を調べておりますが、なにかアドバイスがございましたらよろしくお願いします。

Re: 続・openclが利用できないとの表示

GPU-ZでもOpenCL表示が"not supported"ということですと、やはりまずはここを解消しないと動作しないと思います。

対処方法について、こちらにまとめましたので参照してください。
https://github.com/rigaya/Aviutl-clfilters/blob/master/opencl_load_error.md

Win10/11環境しか手元にないので、Win7では異なる可能性もありますが、適宜読み替えるなどして参考となれば幸いです。

よろしくお願いいたします。

続・openclが利用できないとの表示

お返事が遅くなり申し訳ありませんでした。

結果から申し上げますと、提示いただいた内容の確認と作業を行ってもopenclが使用可になることはございませんでした。
これがOSによるソフトウェア的なものなのか、ハードウェア的なものなのか当方には判断しかねますが、これ以上管理人さんのお手を煩わせるのもいけないので、今回の報告でopenclに関する一連の案件を終わらせていただこうと思います。
管理人さんには動作保証外のwindows7の案件にも関わらず親身に対応いただきありがとうございました。

Re: 続・openclが利用できないとの表示

OpenCLが残念ながら動作可能とならなかったこと承知しました。おそらくソフト的なものと思いますが、難しそうですね…。

ご連絡ありがとうございました。

ノイズ除去の性能

AviUtlの解説サイトなどでは、性能の良いノイズ除去プラグインとしてNL-Means系フィルタがよく紹介されていますが、clfiltersの各ノイズ除去フィルタとはどちらが優れた性能なのでしょうか?

Re: ノイズ除去の性能

個人的には、Aviutlで実際にフィルタをかけてみていい感じになったものを使用するのが一番だと思います。どのようなノイズ除去を求めているかによって、必要とするものは変わるためです。

ノイズ除去の「性能」をどう考えるかにより、評価は分かれると思います。

以下、ノイズ除去アルゴリズムの専門家ではないので、感覚的な話になります。

ノイズが多く、強力なノイズ除去が必要であれば、NL-Means系が優れていると思います。一方、副作用も強く、また一般に処理も重いのではないかと思います。

clfiltersに関しては、もともとがGPUエンコードと一緒に使うことを想定していたものなので、重いフィルタは実装していません。

knnは強めのノイズ除去ですが副作用も多めで高速です。

pmd/smoothはパラメータにもよりますが、相対的にノイズ除去効果は弱めですが副作用も控えめだと思います。計算速度はパラメータによるので一概には言えませんが、そこまで重いという印象はありません。

Re: ノイズ除去の性能

ご回答ありがとうございます。
一つずつ試すことにします。

・・・と思ったのですが、GT 1030だと「メモリ割り当て失敗」という旨のエラーが出てしまい、使えませんでした。(clfilters)
さすがにローエンドなので仕方ない気もしますが、clfiltersの最低および推奨GPUはどれほどになりますか?

Re: Re: ノイズ除去の性能

> clfiltersの最低および推奨GPU
最低条件は、「OpenCLが動作するGPUであること」ですので、NVIDIA/AMD GPUであればおおむねOK、Intel 内蔵GPUだとIvyBridge以降です。

メモリの問題であれば、もしお持ちであればまずはIntel 内蔵GPUで試してみるのがよいかもしれません。

「推奨GPU」は、商用ソフトのようにそうした広範な検証は行っていないのでわかりませんが、開発時の検証では、Geforce GTX1060、Radeon RX460、12900Kの内蔵GPUでは問題なく動作しました。
プロフィール

rigaya

Author:rigaya
アニメとか見たり、エンコードしたり。
連絡先: rigaya34589@live.jp
github twitter

最新記事
最新コメント
カテゴリ
月別アーカイブ
カウンター
検索フォーム
いろいろ
公開中のAviutlプラグインとかのダウンロード

○Aviutl 出力プラグイン
x264guiEx 3.xx
- x264を使用したH264出力
- x264guiExの導入紹介動画>
- x264guiExの導入
- x264guiExのエラーと対処方法>
- x264.exeはこちら>

x265guiEx
- x265を使用したH.265/HEVC出力
- x265guiExの導入>
- x265.exeはこちら>

QSVEnc + QSVEncC
- QuickSyncVideoによるHWエンコード
- QSVEnc 導入/使用方法>
- QSVEncCオプション一覧>

NVEnc + NVEncC
- NVIDIAのNVEncによるHWエンコード
- NVEnc 導入/使用方法>
- NVEncCオプション一覧>

VCEEnc + VCEEncC
- AMDのVCE/VCNによるHWエンコード
- VCEEnc 導入/使用方法>
- VCEEncCオプション一覧>

svtAV1guiEx
- SVT-AV1によるAV1出力
- svtAV1guiExの導入>
- SVT-AV1単体はこちら>

VVenCguiEx
- VVenCによるVVC出力
- VVenCguiExの導入>

ffmpegOut
- ffmpegを使用した出力
- ffmpegOutの導入>


○Aviutl フィルタプラグイン
自動フィールドシフト (ミラー)
- SSE2~AVX512による高速化版
- オリジナル: aji様

clfilters 
- OpenCLベースの複数のGPUフィルタ集
- 対応フィルタの一覧等はこちら

エッジレベル調整MT (ミラー)
- エッジレベル調整の並列化/高速化
- SSE2~AVX512対応
- オリジナル: まじぽか太郎様

バンディング低減MT (ミラー)
- SSE2~AVX512による高速化版
- オリジナル: まじぽか太郎様

PMD_MT
- SSE2~AVX512による高速化版
- オリジナル: スレ48≫989氏

透過性ロゴ (ミラー)
- SSE2~FMA3によるSIMD版
- オリジナル: MakKi氏

AviutlColor (ミラー)
- BT.2020nc向け色変換プラグイン
- BT.709/BT.601向けも同梱

○その他
Amatsukaze改造版
- AmatsukazeのAV1対応版

rkmppenc
- Rockchip系SoCのhwエンコーダ

x264afs (ミラー)
- x264のafs対応版

aui_indexer (ミラー使い方>)
- lsmashinput.aui/m2v.auiの
 インデックス事前・一括生成

auc_export (ミラー使い方>)
- Aviutl Controlの
 エクスポートプラグイン版
 エクスポートをコマンドから

aup_reseter (ミラー)
- aupプロジェクトファイルの
 終了フラグを一括リセット

CheckBitrate (ミラー, 使い方, ソース)
- ビットレート分布の分析(HEVC対応)

チャプター変換 (使い方>)
- nero/appleチャプター形式変換

エッジレベル調整 (avisynth)
- Avisynth用エッジレベル調整

メモリ・キャッシュ速度測定
- スレッド数を変えて測定
- これまでの測定結果はこちら

○ビルドしたものとか
L-SMASH (ミラー)
x264 (ミラー)
x265 (ミラー)
SVT-AV1 (ミラー)

○その他
サンプル動画
その他

○読みもの (ミラー)
Aviutl/x264guiExの色変換
動画関連ダウンロードリンク集
簡易インストーラの概要

○更新停止・公開終了
改造版x264gui
x264guiEx 0.xx
RSSリンクの表示
リンク
QRコード
QR