粗大メモ置き場

個人用,たまーに来訪者を意識する雑記メモ

Build OpenCV for GPU version in Jetson TX1

容量に関する問題

OpenCVソースコードからフルでコンパイルするには容量が4GB必要になります。
16GBの容量のTX1にそれは非常に厳しい...

外部メモリ上でのビルド

似たような状況がRaspberryPiにもあるようで、そちらの記事を参照しました。
PkLab - Install OpenCV 3.2 Python/C++ on Raspberry PI

USBをLinuxファイルシステムとして認識させてその上でコンパイルします。

USBの中身のフォーマット

とにかくUSBの中身をLinuxで見れるext2等のフォーマットへと変える必要があります。

sudo fdisk -l

で中身を確認しながらパーティションをクリアできるとありましたが、
私の場合うまく行かなかったので以下のサイトに準拠してフォーマットしました。
How to format a USB flash drive? - Ask Ubuntu


マウント

私の場合/dev/sda1が対象のUSBのデバイス名なので

sudo mkfs -t ext2 /dev/sda1

これでLinuxファイルシステムとしてフォーマットして
次のコマンドでUSBメモリの中身をLinuxファイルシステムから確認する事ができるようになります。

mkdir ~/usbmem
sudo mount /dev/sda1 ~/usbmem

Opencvのダウンロードとコンパイル

大部分はOpenCV: Building OpenCV for Tegra with CUDAを参考にしています。

ソースのダウンロードと所々の修正は[参考文献1]を。
その後contrib moduleをダウンロードするところは[参考文献2]を参照しています。
SIFTとかも使いたいですからね。

git clone https://github.com/opencv/opencv.git
git cherry-pick 10896
git cherry-pick cdb9c
git cherry-pick 24dbb
cd opencv-3.1.0
git clone --depth 1 https://github.com/Itseez/opencv_contrib.git opencv_contrib
cd opencv_contrib
git fetch origin --tags --depth 1
git checkout 3.1.0

Dependencyの解決

依存するパッケージをインストールします。

sudo apt-add-repository universe
sudo apt-get update
sudo apt-get install \
    libglew-dev \
    libtiff5-dev \
    zlib1g-dev \
    libjpeg-dev \
    libpng12-dev \
    libjasper-dev \
    libavcodec-dev \
    libavformat-dev \
    libavutil-dev \
    libpostproc-dev \
    libswscale-dev \
    libeigen3-dev \
    libtbb-dev \
    libgtk2.0-dev \
    pkg-config

準備していない人はPython環境もちゃんと準備しましょう。(下は2.7用)

sudo apt-get install python-dev python-numpy python-py python-pytest

Cmake と make

追記:完全に参考文献1に準拠し直しました。

cmake .. -DWITH_OPENGL:BOOL=ON -DWITH_QT:BOOL=ON -DWITH_CUDA:BOOL=ON -DCUDA_ARCH_BIN="5.2" -DCUDA_ARCH_PTX="5.2" -DCMAKE_BUILD_TYPE=RelWithDebugInfo -DCMAKE_INSTALL_PREFIX=/usr/local -DBUILD_TESTS:BOOL=OFF -DBUILD_PERF_TESTS:BOOL=OFF -DWITH_FFMPEG:BOOL=OFF -DENABLE_NEON:BOOL=ON -DBUILD_EXAMPLES:BOOL=ON -DINSTALL_C_EXAMPLES:BOOL=OFF -DINSTALL_PYTHON_EXAMPLES:BOOL=ON -DOPENCV_EXTRA_MODULES_PATH=../opencv_contrib/modules
以下古いバージョン(不具合あり)

多分どれかがおかしい...
Cmakeですが、参考文献1と2をあわせた手法を取っています。>||
mkdir build && cd build
cmake .. \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_INSTALL_PREFIX=/usr \
-DBUILD_PNG=OFF \
-DBUILD_TIFF=OFF \
-DBUILD_TBB=OFF \
-DBUILD_JPEG=OFF \
-DBUILD_JASPER=OFF \
-DBUILD_ZLIB=OFF \
-DBUILD_EXAMPLES=OFF \
-DBUILD_opencv_java=OFF \
-DBUILD_opencv_python2=ON \
-DBUILD_opencv_python3=OFF \
-DENABLE_PRECOMPILED_HEADERS=OFF \
-DWITH_OPENCL=OFF \
-DWITH_OPENMP=OFF \
-DWITH_FFMPEG=ON \
-DWITH_GSTREAMER=OFF \
-DWITH_GSTREAMER_0_10=OFF \
-DWITH_CUDA=ON \
-DWITH_GTK=ON \
-DWITH_VTK=OFF \
-DWITH_TBB=ON \
-DWITH_1394=OFF \
-DWITH_OPENEXR=OFF \
-DCUDA_TOOLKIT_ROOT_DIR=/usr/local/cuda-8.0 \
-DCUDA_ARCH_BIN=5.3 \
-DCUDA_ARCH_PTX="" \
-DINSTALL_C_EXAMPLES=OFF\
-DINSTALL_TESTS=OFF \
-DOPENCV_EXTRA_MODULES_PATH=../opencv_contrib/modules
|

  • DCMAKE_INSTALL_PREFIX を /sur/localにするか迷う...(よくわかっていない)


次にmakeします。

make -j4 VERBOSE=1

このVERBOSE=1を入れることでエラーが出た時の詳細が出て進めやすくなります。
(エラー出る前提)
よく出たエラーについては下を参照。

make install

最後のこのコマンドでmakeした結果の実行ファイルなどをローカルのPATHの通ったLibなどにコピーします。
(間違っていたら教えてください)

make install

時々sudoでやっているサイトを見るのだけれどどっちが正しいのだろう?うまく行かなかったらsudoで。

sudo ldconfigを行う場合もあるそうな。

エラー集

当然出まくるエラー。

hdf5.h : No such file or directory

もしhdf5.hがあるのにこのエラーが出るなら
Pythonがhdf5を探せていないのが原因。

modules/python/common.cmake の最後の行に以下の2文を追加。

find_package(HDF5)
include_directories(${HDF5_INCLUDE_DIRS})

can't find hdf5.h when build caffe · Issue #156 · NVIDIA/DIGITS · GitHub
build error for python bindings with opencv_contrib modules · Issue #6016 · opencv/opencv · GitHub

onlineMIL.hpp でのエラー

In file included from /home/ubuntu/usbmem/opencv/opencv_contrib/modules/tracking/include/opencv2/tracking/tracker.hpp:48:0,
                 from /home/ubuntu/usbmem/opencv/build/modules/python2/pyopencv_generated_include.h:49,
                 from /home/ubuntu/usbmem/opencv/modules/python/src2/cv2.cpp:12:
/home/ubuntu/usbmem/opencv/opencv_contrib/modules/tracking/include/opencv2/tracking/onlineMIL.hpp:57:23: error: expected unqualified-id before ‘>’ token
 #define  sign(s)  ((s > 0 ) ? 1 : ((s<0) ? -1 : 0))

この場合、同様の定義が他のcppファイルで使われているのが原因。
error building ```opencv_contrib/modules/tracking/include/opencv2/tracking/tracker.hpp``` · Issue #618 · opencv/opencv_contrib · GitHub

onlineMIL.hppにある次の文をカットして
src/omlineMIL.cppへとペーストする。

#define  sign(s)  ((s > 0 ) ? 1 : ((s<0) ? -1 : 0))

cuda_gl_interop.hに関するエラー

/usr/local/cuda-8.0/includes にある同盟ファイルの GL/gl.hのインクルード周りを次のように変更。

//#if defined(__arm__) || defined(__aarch64__)
//#ifndef GL_VERSION
//#error Please include the appropriate gl headers before including cuda_gl_interop.h
//#endif
//#else
#include <GL/gl.h>
//#endif

Webカメラから画像が取れない?

謎。v4l2周りのエラーということはわかっているのだが...。謎。

テスト

Python

python

import cv2
cv2.__version__
print(cv2.getBuildInformation())

Cpp

以下の通りでコンパイル可能。

g++ -ggdb XXXX.cpp -o XXXX `pkg-config --cflags --libs opencv`

ソースの削除について

基本的にsudo make installを済ませたらもとのOpencvのフォルダに用はないです。
jetsonは容量がカツカツなので中でコンパイルした人はデリート推奨。
私は怖いのでまるっとドライブにバックアップしました。
stackoverflow.com

実行の際のコツ(最初に空の関数を呼び出す)

Opencvでは初回の関数呼び出し時にGPUを初期化する的な動作があるため,
実行する際にはとても時間がかかるという問題があります.

実際にOpenCVのフォーラムに問い合わせたところ,
以下のように空のcuda関数を呼び出すことで初期化を済ませることができるという回答を得ました.

cv::cuda::GpuMat test;
test.create(1, 1, CV_8U);

answers.opencv.org