2013年11月19日火曜日

OpenVXがリリースされた



プレスリリース
Khronos Releases OpenVX 1.0 Specification for Computer Vision Acceleration

OpenCVのItseez社も参加

概略
OpenVXは、リアルタイムのモバイル、組み込みをターゲット、OpenCVを補完するものとのこと


OpenCLとの関係は?
今後もウオッチ

OpenCV 2.4.7でOpenCLを試してみた 4

IntelのOpenCLがGPUを認識しなくておかしいと思って調べてみると

リリースノートの下段の Intel Processors Support Matrixに

1st and 2nd Generation Intel® Core™ Processorsは、CPUと記載してある

メイン開発マシンは、core i5 430Mなので、GPUが使えないことが判明。
サブの開発マシンのCPUを調べてみる。

追加 15:10
実際にSDKをインストールしなくてもWikiにGPUのOpenCL対応がまとめてった

サブも対応していない


OpenCVのOpenCL モジュール紹介を訳してみた

当方OpenCLのまったくの初心者なので、誤った解釈をしていたり意味不明な点も多いあるが、OpenCVのOpenCL モジュール紹介を訳してみた。


将来すべてのOpenCLデバイスで実現したいが、現在対応しているのはGPUデバイスのみである

GPUデバイスは、NVidia, AMDの単体GPUデバイスだけでなく、AMD APU, Intel HDのような統合チップも含んでいる

パフォーマンスはデバイスに依存するが、精度はCPUと同じであることをすべてのGPUと環境(Windows, Linux)で確認している


OpenCV OCL モジュールは、OpenCLの知識なしで使用できるようにデザインされている

OpenCV OCL モジュールは、GPUデバイスの可能性を得るアクセラレータとみなすこともできるが、ユーザ自身のカーネルを作成するための取り掛かりとみなすこともできる

OpenCLの知識があれば手助けになるが、カーネルのソースは、OpenCLの勉強に役立つと望んでいる。

カーネルの知識は、既存のOpenCLのカーネルチューニングだけでなく、機能追加に必須である

正しくOpenCLのモジュールを動作させるためには、デバイスベンダーのランタイムが必要である

OCLを使用するには、CMakeで、WITH_OPENCL=ONにしてOpenCVを作成する必要がある(2.4.7のWindows版は、対応しているので不要である)
フラグがオンで、かつ、SDKがインストールされている場合は、OCLモジュールが作成される

AMD’S FFT や BLAS のライブラリがーあれば、WITH_OPENCLAMDFFT=ON, WITH_OPENCLAMDBLAS=ON.を使用できる

OCLのモジュールは、modulesに格納されている

C++のラッパークラスのソースコードは、modules/ocl/srcに、カーネル自身は、modules/ocl/src/openclに格納されている
サンプルは、samples/oclに、精度のテストは、modules/ocl/testに、パフォーマンスは、module/ocl/perfに格納されている


環境変数 OPENCV_OPENCL_DEVICE で使用するOpenCLデバイスを指定できる
(指定方法は略)

あるいは、cv::ocl::setDeviceで指定することもできる。この関数により、OpenCLのランタイムを初期化し、指定のデバイスを計算デバイスとして設定する。


現在、すべてのスレッドは同じコンテキストを共有しており、マルチデバイスには対応していないが、すぐに対応する予定である

4chをサポートすれば、3chもサポートしないといけない。oclMatでは、3chのRGBイメージは、4chを意味しており、3chの場合
4ch目は使用されていない。OpenCVのMatとoclMatとの互換性のためである


開発者ノート
CPUと単体GPU間でのデータ転送のコストは大きいので、アルゴリズムのパイプラインの最初と最後のみデータ転送すべきである
  1. FULL ProfileサポートのOpenCL1.1以降が必要
  2. 現在、OpenCLのコンテキストとコマンドキューは1つある。マルチデバイスとマルチキューを将来サポートしたい
  3. 可能な場合、多くのカーネルは、256のワークグループを使用しているので、デバイスの最大ワークグループ数は256以上必要である。すべてのGPUデバイスは、対応しているが、それ以外のデバイスは対応していない
  4. もしデバイスが、倍精度をサポートしていない場合は、エラーとなる
  5. oclMatは、イメージオブジェクトではなく、バッファオブジェクトを使用している
  6. oclMatでは、3chのRGBイメージは、4chを意味しており、3chの場合4ch目は使用されていない。OpenCVのMatとoclMatとの互換性のためである
  7. oclMatでは、列方向に配置される。(now the alignment factor for step is 32+ byte)  means, m.cols * m.elemSize() <= m.step.となる
  8. ・Mat and oclMat間でのデータ転送 もし、Matが列方向に配置されていると転送は速い。そうでない場合は、アライメントを保証するために、clEnqueueRead/WriteBufferRectを使用する。3chの場合例外で、デバイスに転送される場合に4chに変換される(CPUへの転送は逆になる)
  9. Mat and oclMat間ではROIの扱いが異なる。oclMatでは、ROIが扱えないので、すべての画像がデバイスにいったん転送される。
  10. カーネルのソースは、modules/ocl/src/opencl/の拡張子、.clである。 opencl_kernels.cppで、カーネルは変換され、拡張子のないファイル名がソースのファイル名になる
以上

2013年11月18日月曜日

OpenCV 2.4.7でOpenCLを試してみた 3

2.4.7からOpenCVをビルドしなくてもOpenCLが利用できるようになっている。

OpenCLに関しては、"これからの並列計算のためのGPGPU連載講座(VI)" を参考にさせていただいた


本来なら、前処理など複雑な手順が必要であるが、OpenCVでは、これらの作業が隠避されており、素人に対しての障壁が低くなっている。

OpenCVのOpenCL用の関数のソースが、sources\modules\ocl\srcに格納されているので、気になる人は覗いてみると面白いかもしれない。

ソースの中を覗いているとコマンドキューにコマンドを送る関数 openCLExecuteKernel がメインとなっており、多くのクラスは、ラッパーとなっている。

また、sources\modules\ocl\src\openclにカーネルのソースが格納されており、sources\modules\ocl\src\cl_runtimeにランタイム関連のソースが含まれている

このあたりを参考にすれば、原理的には自前の関数をOCL対応でき、OpenCVから呼び出すことが可能かと考えられるが、当方スキル不足なので実現は無理である。

OpenCV 2.4.7でOpenCLを試してみた 2

2.4.7からOpenCVをビルドしなくてもOpenCLが利用できるようになっている。

使用している開発マシンのOpenCLデバイス情報を調べてみた。
デバイス情報は、cv::ocl::getOpenCLDevicesを用いて、cv::ocl::DevicesInfoを取得することで得られる。

最初、deviceTypeを指定しないと、DevicesInfoのsizeが0になり焦ったが、deviceTypeにCVCL_DEVICE_TYPE_CPUを指定することでデータを取得できた。

本来ならコンソールに各情報を取得するプログラムを書きたかったが、手抜きでデバッガーで変数を表示させている




気になる値
local Memory size  個々のWorkGroup用のローカルメモリーは32kである
Max memory allocation size  ?は、約511Mである

2013年11月15日金曜日

OpenCV 2.4.7でOpenCLを試してみた 1

2.4.7からOpenCVをビルドしなくてもOpenCLが利用できるようになっている。

1 準備
最初に自分の環境あったデバイスのOpenCL SDKをインストールしておく

GPUを所持していないので、Intel版で試す。
IntelのSDKは、ここからダウンロードする。


注意
Visual studio 2010 Express Editionを使用しているとき、インストール途中のVisual studio 2010のチェックをはずすこと


2 動作テスト
sources\samples\oclにサンプルのコードがあるが、テストプログラムを作成

OCL関連のヘッダーとライブラリを加える

#include <opencv2/ocl/ocl.hpp>
#pragma comment(lib,"opencv_ocl247d.lib")


ソース(コアのみ)

int main(int argc, char** argv)
{
cv::Mat matIn = cv::imread("c:\\hoge.png"), matDisp;
cv::imshow("Color", matIn);

cv::ocl::oclMat oclIn(matIn), oclOut;

cv::ocl::cvtColor(oclIn, oclOut, cv::COLOR_BGR2GRAY);

oclOut.download(matDisp);

cv::imshow("Gray",matDisp);

cv::waitKey(0);

return 0;
}

テストプログラムでは、白黒に変換している。

起動すると、絵が表示されるまでに10秒近く時間がかかる。


注意
  • OCLは、実行時に環境にあわせたカーネルソースがバイナリにコンパイルされるため、オーバヘッドが大きいので、よく使用する関数は、起動時にダミーを呼んでおくのがよいそうだ。
  • メモリーと対象デバイス間の転送時間がかかるため、サイズの大きい画像でないとメリットはない
  • ネットには事前に、ocl::getDeviseを呼ぶようにとかかれたものがあるが、2.4.7では必要ないし、そのような関数はなくなっている

追加11/15 17:50 未確認
 当方の環境 OpenCL対応デバイスが、Intel CPUのみなので初期化が不要であったが、グラフィックスボードを追加し、ボードに対応したOpenCL SDKをインストールした場合には、ocl::setDeviceを呼ぶ必要があるかもしれない



関連ドキュメント

OpenCV関連のkindle本が安い

11/15での価格 改定される可能性あり

Mastering OpenCV With Practical Computer Vision Projects
ペーパ 4661円 kindle 1853円

Android Application Programming with Opencv
ペーパ 3629円 kindle 1447円


amazonにこんなマニアックなカテゴリが
Artificial Intelligence Machine Vision の ベストセラー