CUDAありのOpenCVをbuildしたった(Ubuntu18.04)

# Background
[OpenCV Advent Calendar 2020](https://qiita.com/advent-calendar/2020/opencv)で何か書こうと思って、最新のOpenCVのversionである4.5をbuildしたのですが思いの外にエラーが出て半日かかってしまいました。:scream:
どうやったらbuildできたか、または失敗したかを書いていきます。

# Points
結局のところ、

1. cuda系のドライバー・ライブラリを削除、再インストールする
2.  ~~OpenCV のソースコードはgithubでcloneするのではなく、圧縮ファイルを使った方が良い~~ git cloneでも問題なくbuild出来た。時々commitされているコードが他のパッケージに影響を受けてerrorになっている場合があるっぽい(2020/12/7)
3. Ubuntu18.04を使っていたためか、gccのversionは6系にセットする

でbuildが成功しました。

### cuda系のドライバー・ライブラリを削除、再インストールする

まず、既にインストールされているパッケージ・ライブラリを削除する。
([UbuntuにNvidia GPUのDriver + CUDAをInstallする(GTX1080対応版)](https://qiita.com/conta_/items/d639ef0068c9b7a0cd12)をみたった。)

```shell
sudo apt-get --purge remove nvidia-*
sudo apt-get --purge remove cuda-*
```

[CUDA Toolkit 11.1 Update 1 Downloads](https://developer.nvidia.com/cuda-downloads)から最新版をダウンロードしてインストールします。
runfile自体3GBととても重いです。リポジトリをインストールしてその後でaptを使ってインストールする方法があるのですが、正常に安定的に作動させるにはこちらが確実かもしれません。

```shell
wget https://developer.download.nvidia.com/compute/cuda/11.1.1/local_installers/cuda_11.1.1_455.32.00_linux.run
sudo sh cuda_11.1.1_455.32.00_linux.run

#完了後にサーバを再起動
sudo reboot
```

で、下記のコマンドでversionが表示できるか確認。

```shell
#nvidia driver
nvidia-smi
#cuda
nvcc -V
```

次にDeep Learning用のライブラリであるcuDNNをインストールします。
[nvidia公式](https://developer.nvidia.com/cuDNN)からパッケージをダウンロードするのですが事前にサインインする必要があります。ダウンロード後はdpkgを使ってインストールします。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/288206/11c3341c-519c-a630-3579-6a02b86052fa.png" width="75%">

```shell
sudo dpkg -i libcudnn8_8.0.5.39-1+cuda10.1_amd64.deb
sudo dpkg -i libcudnn8-dev_8.0.5.39-1+cuda11.1_amd64.deb
sudo dpkg -i libcudnn8-samples_8.0.5.39-1+cuda11.1_amd64.deb
```

### ~~OpenCV のソースコードはgithubでcloneするのではなく、圧縮ファイルを使った方が良い~~ git clone, 圧縮ファイルのどちらを使っても結局は良さそう (2020/12/7)

[OpenCV Installation in Linux](https://docs.opencv.org/master/d7/d9f/tutorial_linux_install.html)や他の開発者のページを見るとgithubでcloneしてソースファイルをダウンロードしています。

```shell
git clone https://github.com/opencv/opencv.git
cd opencv
#最新版にチェックアウト
git checkout -b 4.5.0
cd ../
git clone https://github.com/opencv/opencv_contrib.git
#最新版にチェックアウト
cd opencv_contrib
git checkout -b 4.5.0
```

使っているマシンの相性が悪いためかその後buildするとエラーが出てしまって失敗します。
おそらく、世界中の開発者がリアルタイムでコミットしてて、他のパッケージに影響が出ているから、と思ってたりします。
なので、https://github.com/opencv/opencv/releases、https://github.com/opencv/opencv_contrib/releases から圧縮ファイルをダウンロードして解凍した方が確実だと思います。

再度、`git clone` にてbranchが`master`であるのと`４.５.0`の両方buildしてみたのですが、どちらとも正常にbuild出来ました。しかし、ときどきコミットがミスっている可能性がありそうなので`git clone`でbuild errorが出る場合は、圧縮ファイルを使った方が良さそう。
(2020/12/7)

```
wget https://github.com/opencv/opencv/archive/4.5.0.tar.gz
tar -zxvf 4.5.0.tar.gz
wget https://github.com/opencv/opencv_contrib/archive/4.5.0.tar.gz
tar -zxvf 4.5.0.tar.gz
```

### Ubuntu18.04を使っていたためか、gccのversionは6系にセットする

```sh
 ./
　├ build/
　├ opencv-4.5.0/
　├ opencv_contrib-4.5.0/
```
とフォルダの構成にします。

それで、 `cd build` で移動してcmakeコマンドを打つのですが、もしエラーが続く場合は先頭に`CC=gcc-6 CXX=g++-6`を付けてgccのバージョンをセットすると良いです。あとは、`-D CMAKE_CXX_FLAGS="-std=c++17"` でc++のバージョンを変えてみたらいいかな。

```sh
CC=gcc-6 CXX=g++-6 cmake -D CMAKE_BUILD_TYPE=RELEASE \
 -D CMAKE_CXX_FLAGS="-std=c++17" \
 -D CMAKE_INSTALL_PREFIX=/usr/local/lib/opencv4.5 \
 -D OPENCV_EXTRA_MODULES_PATH=../opencv_contrib-4.5.0/modules \
 -D INSTALL_C_EXAMPLES=ON \
 -D INSTALL_TESTS=ON \
 -D WITH_MKL=OFF \
 -D WITH_CUDA=ON \
 -D CUDA_FAST_MATH=ON \
 -D WITH_CUDNN=ON \
 -D ENABLE_FAST_MATH=ON \
 -D CUDA_ARCH_BIN=5.2 \
 -D CUDA_ARCH_PTX=5.2 \
 -D BUILD_EXAMPLES=ON \
 -D WITH_TBB=ON \
 -D BUILD_TBB=ON \
 -D WITH_V4L=ON \
 -D WITH_QT=ON \
 -D WITH_GTK=ON \
 -D CVV_DEBUG_MODE=ON \
 -D WITH_OPENCL=ON \
 -D WITH_OPENGL=ON \
 -D OPENCV_SKIP_DLLMAIN_GENERATION=ON \
 -D BUILD_opencv_python2=OFF \
 -D BUILD_opencv_python3=ON \
 -D INSTALL_PYTHON_EXAMPLES=ON \
 -D WITH_PYTHON=ON \
 -D PYTHON_DEFAULT_EXECUTABLE=python3 \
 -D PYTHON3_NUMPY_INCLUDE_DIRS=/home/kai_walker/.local/lib/python3.6/site-packages/numpy/core/include \
 ../opencv-4.5.0
```

あとは、

```bash
sudo make install
ldconfig
```
で完了。

作成したlibファイルは `-D CMAKE_INSTALL_PREFIX=/usr/local/lib/opencv4.5` で指定したフォルダに保管されます。

# PostScripts

build時のオプションは何使えばいいかよくわからんすね。 CUDAの場合は `WITH_CUDA=ON` 以外何設定すればいいかです。まとまったページがあればいいんだけど、現状では `CMakeLists.txt` のMakeファイル見るしかないか。 

# Reference

- [OpenCV 4.1.0をWindowsでビルドする手順](https://qiita.com/KurozumiGH/items/ef8cca96a13444b7dcda)
- [OpenCV Installation in Linux](https://docs.opencv.org/master/d7/d9f/tutorial_linux_install.html)
- [cudacodecモジュールを使ってみよう](https://qiita.com/dandelion1124/items/fb12461e41e70ccc161e)
- [OpenCVのビルドインストール（CUDA対応環境用）](https://qiita.com/orphiria/items/3b8ba0c3e23144d3f4df)
- [OpenCV 4.3.0 (最新版) のビルドとインストール，CUDA 対応可能（ソースコードを使用）（Ubuntu 上）](https://www.kkaneko.jp/tools/ubuntu/ubuntu_opencv_buildout.html)
- [CUDA cuDNNのインストール手順](https://mmm-ssss.com/2019/10/01/cuda-cudnn%E3%81%AE%E3%82%A4%E3%83%B3%E3%82%B9%E3%83%88%E3%83%BC%E3%83%AB%E6%89%8B%E9%A0%86/)
- [CUDA，cuDNNのバージョン確認
](https://blog.mktia.com/get-cuda-and-cudnn-version/)
- [UbuntuにNvidia GPUのDriver + CUDAをInstallする(GTX1080対応版)](https://qiita.com/conta_/items/d639ef0068c9b7a0cd12)
- [Ubuntu18.04にCUDA10.1+cuDNN7.6.5+tensorflow-2.3.0をインストール](https://qiita.com/masamiic/items/08857765e9d0b9431172)