ubuntu16.04でopenpose環境構築

#研究室に機械学習用PCが届いた！
GeForceが4台、CPUが2台載ってるぞ！メモリも90GBある！
ついにうちの研究室も「プログラム回すのに1週間かかります＾＾；」って言えるように・・・！！
さて何をしようか、研究で人の運動とかやってるしとりあえずopenposeでもやってみるか．

#Cuda9.0をアンインストール
機械学習用PCとして購入したので，初期設定でCuda9.0とかが入っている.
openposeはCuda8.0じゃないと動かないらしい．
じゃあCuda9.0はアンインストールして，Cuda8.0をインストール！
##Cuda9.0をアンインストール
```Bash
sudo apt purge cuda*
sudo apt purge nvidia-cuda-*
sudo apt purge libcuda*
```
##Cuda8.0をインストール
下記URLからCUDA Toolkit 8.0 GA2 (Feb 2017)のdeb(local）を落とす．
https://developer.nvidia.com/cuda-toolkit-archive

```Bash
sudo dpkg -i cuda-repo-ubuntu1604-8-0-local-ga2_8.0.61-1_amd64.deb
sudo apt-get update
sudo apt-get install cuda-8-0

sudo dpkg -i cuda-repo-ubuntu1604-8-0-local-cublas-performance-update_8.0.61-1_amd64.deb 
sudo apt-get update
sudo apt-get upgrade
```
##パスの設定
```Bash
echo -e "\n## CUDA and cuDNN paths"  >> ~/.bashrc
echo 'export PATH=/usr/local/cuda-8.0/bin:${PATH}' >> ~/.bashrc
echo 'export LD_LIBRARY_PATH=/usr/local/cuda-8.0/lib64:${LD_LIBRARY_PATH}' >> ~/.bashrc
source ~/.bashrc # CUDAのパスが書き込まれた~/.bashrcを読み込む。
```
```Bash
## CUDA and cuDNN paths
export PATH=/usr/local/cuda-8.0/bin:${PATH}
export LD_LIBRARY_PATH=/usr/local/cuda-8.0/lib64:${LD_LIBRARY_PATH}
```
```Bash
echo $PATH             # 出力に"/usr/local/cuda-8.0/bin"が含まれているか？
echo $LD_LIBRARY_PATH  # 出力に"/usr/local/cuda-8.0/lib64"が含まれているか？
which nvcc             # 出力が"/usr/local/cuda-8.0/bin/nvcc"になっているか？
nvidia-smi             # nvidiaのGPUの情報が表示されているか？
```
##nvidia-smiなんかないよって怒られる
一回再起動してみよう．

##cuDNN6.0を入れる．
[NVIDIA cudnn-download](https://developer.nvidia.com/rdp/cudnn-download )からuDNN 6 for CUDA 8.0のdebパッケージをダウンロードする．
メンバーシップ登録が必要なので登録しよう．

- cuDNN v6.0 Runtime Library for Ubuntu16.04 (Deb)
- cuDNN v6.0 Developer Library for Ubuntu16.04 (Deb)
- cuDNN v6.0 Code Samples and User Guide for Ubuntu16.04 (Deb)
をダウンロードして，

```Bash
sudo dpkg -i libcudnn6_6.0*+cuda8.0_amd64.deb
sudo dpkg -i libcudnn6-dev_6.0*+cuda8.0_amd64.deb
sudo dpkg -i libcudnn6-doc_6.0*+cuda8.0_amd64.deb
```

##参考
下記のサイト参考にさせていただきました．
本当に感謝しております．
[Ubuntu16.4 でＣUDA9をアンインストールしてＣＵＤＡ８を入れる](http://tako104.way-nifty.com/blog/2017/12/ubuntu164-uda9-.html)
[https://qiita.com/JeJeNeNo/items/05e148a325192004e2cd](https://qiita.com/JeJeNeNo/items/05e148a325192004e2cd)


# OpenCV3.1.0を入れる．
##依存モジュールをインストールする
```Bash
sudo apt-get update
sudo apt-get upgrade
sudo apt-get install \
        build-essential \
        cmake \
        git \
        pkg-config \
        libjpeg8-dev \
        libtiff5-dev \
        libjasper-dev \
        libpng12-dev \
        libavcodec-dev \
        libavformat-dev \
        libswscale-dev \
        libv4l-dev \
        libatlas-base-dev \
        libgtk2.0-dev \
        gfortran
```
##OpenCVのソースコードを取得
githubより取得

```Bash
git clone git://github.com/opencv/opencv
cd opencv
git checkout 3.1.0
```
```Bash
git clone git://github.com/opencv/opencv_contrib
cd opencv_contrib
git checkout 3.1.0
```
##ビルドする

```Bash
mkdir ~/opencv/build
cd ~/opencv/build
cmake \
    -D CMAKE_BUILD_TYPE=RELEASE \
    -D CMAKE_INSTALL_PREFIX=/usr/local \
    -D OPENCV_EXTRA_MODULES_PATH=~/opencv_contrib/modules \
    -D BUILD_EXAMPLES=ON \
    -D INSTALL_PYTHON_EXAMPLES=ON \
```
##ビルドできない！！
OpenCV3.1.0はCuda8.0に対応していないと怒られる，そんなぁ...
いろいろググると同じ問題にぶち当たっている人が見つかる．
[Github : opencv3.10 does not support cuda8.0rc?](https://github.com/opencv/opencv/issues/6677)
これによると，with-cuda8なるものがあるらしい．愚直に従う．

```Bash
git clone https://github.com/daveselinger/opencv
git checkout 3.1.0-with-cuda8
```
_contribは見つからないので，さっきクローンしたやつを使う．

##ついでにCMakeGUIをここで使いはじめる．

```Bash
sudo apt-get install cmake-qt-gui
````
GUIを起動して，”Where is the source code”に"opencv"，”Where to build the binaries"に"opencv/build"を選択して左下のConfigureする.
ウィンドウが2個ぐらい出てくるので，全部FinishでOK．
Name，Valueのところにずらずらっと出てくるので，上記で示した

```Bash
    -D CMAKE_BUILD_TYPE=RELEASE \
    -D CMAKE_INSTALL_PREFIX=/usr/local \
    -D OPENCV_EXTRA_MODULES_PATH=~/opencv_contrib/modules \
    -D BUILD_EXAMPLES=ON \
    -D INSTALL_PYTHON_EXAMPLES=ON \
    ..
```
に当てはまる項目を探していって，上記通りの場所が指定されていなかったら指定する．

##ippicvがないと怒られる
またビルドできない，週6で筋トレしてる自分でも心が折れそうになる．
ググると同じ問題に直面している人がいる．
[Github : incorrect hash in cmake ippicv when installing](https://github.com/opencv/opencv/issues/5973)
ここらへんでエラー名で検索するだけで，解決方法がでてくることがわかり折れそうな心に支えができる．
どうやら，直接tgzファイルを置けばいいだけらしい．
下記URLからダウンロードして，
[Github : opencv/opencv_3rdparty](https://github.com/opencv/opencv_3rdparty/tree/ippicv/master_20151201)
ippicv_linux_20151201.tgzを
opencv-3.1.0/3rdparty/ippicv/downloads/linux-808b791a6eac9ed78d32a7666804320e/
に置く．

##onlineMILでエラー
エラーの内容を忘れたけど，定義されていない？的なエラーが吐かれてビルドできない．
またもやgoogle先生．
[Github : error building opencv_contrib/modules/tracking/include/opencv2/tracking/tracker.hpp](https://github.com/opencv/opencv_contrib/issues/618)
opencv_contrib/modules/tracking/include/opencv2/tracking/onlineMIL.hppの中身を少し書き換えればいいらしい．

```C++
#define  sign(s)  ((s > 0) ? 1 : ((s<0) ? -1 : 0))
```
を

```C++
#define  CV_SIGN(s)  (((s) > 0) ? 1 : (((s)<0) ? -1 : 0))
```
に書き換えればいい．
なんかもう一回エラー出た気がするけど，「sign(s)が定義されていません」的なやつだったと思うので，
そこのsign(s)をCV_SIGN(s)に書き換えれば通った．

##ビルドできた！！
makeする．

```Bash
make -j2
sudo make install
```
ちゃんとできてるか確認する．

```Bash
python
Python 2.7.12 (default, Nov 12 2018, 14:36:49) 
[GCC 5.4.0 20160609] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import cv2
>>> cv2.__version__
'3.1.0'
```
##参考
参考にさせていただきました．めっちゃ感謝しています．ここ見なかったらビルドできていませんでした．
[Ubuntu Desktop 16.04上で、OpenCV3.1.0をビルドする](http://thaim.hatenablog.jp/entry/2016/07/11/004631)

#ここからやっとopenpose
かなり書いた気がするけど，ここからやっとopenposeの環境構築．
[本家](https://github.com/CMU-Perceptual-Computing-Lab/openpose/blob/master/doc/installation.md)を参考に進めていく．

##注意！！
本家の通りやっていくと

```Bash
sudo bash ./ubuntu/install_cmake.sh
```
が推奨されているが，これをしてしまうとcuDNN5.1 が勝手に入れられてしまう．
さきほど，cuDNN6.0を入れたところなのでこれを使うのは控えておく．

##まずはopenposeのクローン

```Bash
git clone https://github.com/CMU-Perceptual-Computing-Lab/openpose
```
###3rd partyにcaffeをクローンする

```Bash
cd openpose/3rdparty
git clone https://github.com/BVLC/caffe.git
```
###これで良いと思いきや．．．
結論から言うと，openposeのビルドまではできるけどpythonのexample動かそうとするとエラーが吐かれる．
[Github : example runtime error:message_lite.cc:123 Can't parse message of type "caffe.NetParameter"](https://github.com/CMU-Perceptual-Computing-Lab/openpose/issues/787)
読んでいくとタイポがあるらしい？
[Github : fix typos and some minor fixes.](https://github.com/BVLC/caffe/commit/f019d0dfe86f49d1140961f8c7dec22130c83154)
さっきクローンしたcaffeをチェックアウトすれば解決するらしい．

```Bash
cd openpose/3rdparty/caffe
git checkout f019d0dfe86f49d1140961f8c7dec22130c83154
```

## Caffeをビルド
GUIを起動して，”Where is the source code”に"openpose/3rdparty/caffe"，”Where to build the binaries"に"openpose/3rdparty/caffe/build"を選択して左下のConfigureする.

###OpenCVが無いと怒られる
OpenCV_CONFIG_FILEに下記の情報を入れる．
OpenCV_CONFIG_FILE="/usr/local/share/OpenCV/OpenCVConfig.cmake"
OpenCV_DIRにも同じような感じで，
OpenCV_DIR="/usr/local/share/OpenCV
を入れる．
それらを挟んで"OpenCV_FOUND"っていうチェックボックスが2つあるので両方共チェックいれる（あんまりよくわかってないけど，チェック入れないとうまくいかない）．
そしてもう一度ConfigureとGenerate.
Generateすると何かエラー吐かれるけど，Gererate Doneになるので，

```Bash
cd opencv/3rdparty/caffe/build
make all
```

##opsenposeをビルド
CudaやらcuDNNやらはすでに終わっていて，CMake GUIも既にインストール済みなので，OpenPose Configurationの部分から見ていく．
本家通りにCmake GUIを操作していく．
Pythonのサンプルを動かすので，BUILD_PYTHONにはチェックを入れる．

###またOpenCVが無いと怒られる
上記と同じようにする．

##Caffeはビルドしたものを使う
BUILD_CAFFEにチェックが入った状態でConfigureすると，
Caffe_INCLUDE_DIRS
Caffe_LIBS
が出てきて，not foundになっているので，さっきビルドしたものを入れる．
Caffe_INCLUDE_DIRS="/home/user/openpose/3rdparty/caffe/build/include"
Caffe_LIBS="/home/user/openpose/3rdparty/caffe/build/lib/libcaffe.so"

もう一回ConfigureしてGenerateする．

##ビルドできた！！

```Bash
cd openpose/build
make -j`nproc`
sudo make install
```
多分，できる．できなかったらエラー名で検索してみてください．

##参考
参考にさせていただきました．基本，ここを参考にさせて頂いたのでめっちゃ感謝してます．
[Soccer On Your Tabletop を AWS で動かして、HoloLens にデプロイしてみた](https://qiita.com/nichyou/items/04699b1d455b23ae1f21)

#サンプルを動かしてみる
ビルドしたexamplesをやってみる．

```Bash
cd openpose/build/examples/tutorial_api_python/
python 1_extract_pose
```

野球選手がベース踏んでるところの画像が出てきて，detectの結果が表示されたら成功．
プログラムは勝手に終了しないみたいだけど，これであってるのかな...（Ctrl + Cで強制終了した）.

#[番外]openpose/build/examples/openpose/openpose.binのprotobuf問題...
[OpenPose - Quick Start](https://github.com/CMU-Perceptual-Computing-Lab/openpose/blob/master/doc/quick_start.md#quick-start)のopenpose.binを使ったサンプルが動かないです...

```Bash
user@Ubuntu:~/openpose/build/examples/openpose$ ./openpose.bin --image_dir examples/media/
[libprotobuf FATAL google/protobuf/stubs/common.cc:79] 
This program was compiled against version 2.6.1 of the Protocol Buffer runtime library, 
which is not compatible with the installed version (3.5.1).  
Contact the program author for an update.  
If you compiled the program yourself, make sure that your headers are from the same 
version of Protocol Buffers as your link-time library.  
(Version verification failed in
 "/build/mir-O8_xaj/mir-0.26.3+16.04.20170605/obj-x86_64-linux-gnu/src/protobuf/mir_protobuf.pb.cc".)
terminate called after throwing an instance of 'google::protobuf::FatalException'
  what():  This program was compiled against version 2.6.1 of the Protocol Buffer runtime library,
 which is not compatible with the installed version (3.5.1). 
 Contact the program author for an update.  
If you compiled the program yourself, make sure that your headers are from the same 
version of Protocol Buffers as your link-time library.  
(Version verification failed in
 "/build/mir-O8_xaj/mir-0.26.3+16.04.20170605/obj-x86_64-linux-gnu/src/protobuf/mir_protobuf.pb.cc".)
中止 (コアダンプ)
```
protobufのバージョンが新しいからダメって言われていて，
[This program requires version 3.3.0 of the Protocol Buffer runtime library](https://github.com/BVLC/caffe/issues/5711)
とか見ながら

```Bash
sudo pip uninstall protobuf
sudo pip install protobuf == 2.6.1
```
等やってみたのですが，そういう問題でもないらしく

```Bash
user@Ubuntu:~$ protoc --version
libprotoc 3.5.1
user@Ubuntu:~$ which protoc
/usr/local/bin/protoc
```
PATH変更して，

```Bash
user@Ubuntu:~$ protoc --version
libprotoc 2.6.1
user@Ubuntu:~$ which protoc
/usr/bin/protoc
```
にしてみても同じエラーが吐かれました...
解決策あれば教えていただけると幸いです．


##追記:2019/3/29
更新するのがかなり遅れましたが，実はあの後OpenPose動くようになりました．
結局，動かなかった原因はCaffeにあるようです．
優秀な後輩が別のVer.のCaffeを参照するようにしたところ，動くようになりました．
もし同じエラー吐かれた場合はCaffeをPullする際に，別のver.でチェックアウトするようにしてトライしてみてください．
ちなみに動くとGPUフル回転になり，GeForce1080が4台搭載の場合1000W近くまで上昇しますので注意してください...（僕の場合，UPSの容量上回ってシャットダウンしました）