Ubuntu18.04でのChainer環境構築

# はじめに
+ 基本的に研究室内部向けの資料なので、状況設定が限定的かも。
+ chainerの環境構築関連の記事があまりに見つからないため、一応公開にした。
+ 状況設定
    + Ubuntu18.04
    + sudoは持っていない
    + Cudatoolkit11.2インストール済み
    + Anaconda仮想環境(今回はpython==3.7)
    + cudnnは入れていない
    + 2021.03.09現在の状況。cupy-cuda112の入れ方が変なのとかは多分今だけ。

# 用語
調べていると色々な用語が出てくるため、初学者(私)は混乱しがち。わかりやすいので[ここ
](https://qiita.com/s059ff/items/f8127dc5e5b8cc15a4c3)見て。ここには上サイトのうち私の理解と異なるものや追記したいものだけ取り上げた。

+ cupy…Python の標準数値計算ライブラリ numpy の GPU 移植版。現在はcudatoolkitのバージョンに合わせて"cupy-cudaXXX"としてインストールするため、cupyとcupy-cudaは同一視して問題ない。
+ cuDNN…CUDA を用いてディープラーニングをする際に利用**可能**なライブラリ。chainerとかpytorchとかを動かすときにも、プログラムの変更無しに動作が速くなる。
+ cudatoolkit…CUDAを利用するためにインストールするツールキット。実質こいつのバージョンがcudaのバージョン。

# 成功パターン
結論うまくいったのだけ先に書いとく。諸々の失敗は後の方に書いた。結論chainer7系列が悪さしてて、6系列なら色々動きそう。
## パッケージとバージョン
chainerを動かすのに最低限必要なパッケージ

+ chainer==6.7.0
+ cupy-cuda112==8.5.0
+ cudatoolkit11.2(大元の環境に11.2をインストール済み)

## 入れ方
```shell
$ pip install cupy-cuda112 -f https://github.com/cupy/cupy/releases/v8.5.0
$ conda install chainer==6.7.0
```
大元の環境のcudatoolkit11.2に合わせてcupy-cuda112をインストール。入れ方が特殊なのは[公式のgit](https://github.com/cupy/cupy/issues/4704)見て。
詳細は後に記載するが、chainer7系列だと何故かcupyが利用不可になる。cupy-cudaやcudatoolkitの組み合わせは色々試したが結局chainer6系列の最新までは落とさないと動かなかった。

## 確認方法
```shell
$ python
>>> import chainer
>>> chainer.print_runtime_info()
Platform: Linux-5.4.0-66-generic-x86_64-with-debian-buster-sid
Chainer: 6.7.0
ChainerX: Not Available
NumPy: 1.20.1
CuPy:
  OS                           : Linux-5.4.0-66-generic-x86_64-with-debian-buster-sid
  CuPy Version                 : 8.5.0
  NumPy Version                : 1.20.1
  SciPy Version                : None
  Cython Build Version         : 0.29.22
  CUDA Root                    : /usr/local/cuda
  CUDA Build Version           : 11020
  CUDA Driver Version          : 11020
  CUDA Runtime Version         : 11020
  cuBLAS Version               : 11401
  cuFFT Version                : 10400
  cuRAND Version               : 10203
  cuSOLVER Version             : (11, 1, 0)
  cuSPARSE Version             : 11400
  NVRTC Version                : (11, 2)
  Thrust Version               : 101000
  CUB Build Version            : 101000
  cuDNN Build Version          : None
  cuDNN Version                : None
  NCCL Build Version           : 2804
  NCCL Runtime Version         : 2804
  cuTENSOR Version             : None
  Device 0 Name                : GeForce GTX 1080 Ti
  Device 0 Compute Capability  : 61
  Device 1 Name                : GeForce GTX 1080 Ti
  Device 1 Compute Capability  : 61
  Device 2 Name                : GeForce GTX 1080 Ti
  Device 2 Compute Capability  : 61
iDeep: Not Available
```
これの結果でcupyが"Not Available"じゃなければおｋ

## 失敗した組み合わせ
結論chainer7系列にしようとしたのが諸問題の原因だった。色々試したけどどれもダメだったので一応記録しておく。
調べた中で見つけた[新しめの記事](https://izumo27.hatenablog.com/entry/2020/11/21/195100)のやり方を参考にやってみた。尚、nvccにパスは通してても通してなくても結果は変わらなかったため、最終的には通していない。
全部試した後に記事を書いているので、cupyが動かなかったのかchainerも動かなかったのか記憶が朧げ。

### パターン1：cupy-cuda112, chainer7.7.0
成功パターンのchainerが新しい例。condaの最新はcupy-cuda110, chainer6.3.0だったので、双方の最新をpip経由で入れた。

```shell
$ pip install cupy-cuda112 -f https://github.com/cupy/cupy/releases/v8.5.0
$ pip install chainer
```
chainerは動いたがcupyが認識されず。尚cupy-cuda112は8.5.0でも9.0.0b3でもダメだった。

### パターン2：cupy-cuda112(conda), chainer7.7.0
[公式のissue](https://github.com/cupy/cupy/issues/4704)にconda-forgeから入れる方法も書いてあったのでやってみた。

```shell
$ conda install -c conda-forge cupy=8.5.0 cudatoolkit=11.2
$ pip install chainer
```
(正直覚えていないが)chainerが動かなかったような気がする。
gitに書いてあったのをそのままコピペするとcondaの中にcudatoolkit11.2が入る。そのまま動かしてダメだったのでcudatoolkit11.2の指定を外したら、cudatoolkit11.0がcondaに入ってきた。結局どちらも動かず。
conda-forge経由で入れると色々ぶっ壊れるので、やるなら全部conda-forgeにすべきみたい。個人的にはpipとconda以上に気を付けないといけなそう。全部conda-forgeに揃えるのは面倒だったので今回は失敗として切り捨てた。[参考](https://waregawa-log.hatenablog.com/entry/2019/01/08/070000)  
色々ダメそうだったのでcupy-cuda112==9.0.0b3は試してない。

### パターン3：condaでcudatoolkitを入れ、他をpipで新しいの入れる
[参考記事](https://izumo27.hatenablog.com/entry/2020/11/21/195100)中で"cupyのバージョン8.0.0が新しすぎたのが原因"とあるので、cupy-cuda110==7.7.0を入れてみた。尚、cupy-cuda112は8.5.0から存在する。
conaで現在最新のcudatoolkit11.0を入れ、それに合わせてpipでcupy-cuda110を入れる。尚、cupy-cudaはなぜかcondaでは見つからない。

```shell
$ conda install cudatoolkit 
$ pip install cupy-cuda110
$ pip install chainer
```
chainerは動く。このパターンではchainerを6.4.0にしたら動いたので多分6.7.0でも動く。最初に紹介した成功パターンではcupy-cuda112==8.5.0なので、"cupyが新しすぎた"ために動かなかった訳ではないんじゃないかなと思った。

# 終わりに
正直色々間違いとかミスとかあると思うので、ご指摘いただけたら幸いです。

# 追記
+ 一応後からcuDNN入れようとしてみたけど、Anaconda仮想環境の上、sudo持ってない、chainer、の条件でやろうとするとまた面倒っぽい。TensorflowとかはAancondaで必要なの全部入るらしい。
+ 上記、pytorch環境ではあるが、conda経由で普通にcuDNNを入れられたので、問題なく入れられるかも。筆者が既にchainerを使ったプロジェクトを動かしていないので未検証。今後試すかも。(2021.06.23追記)

# 参考
+ [公式のインストールページ](https://docs.chainer.org/en/stable/install.html)
+ [公式のgithubのissue](https://github.com/cupy/cupy/issues/4704)
+ [主に参考にしたページ](https://izumo27.hatenablog.com/entry/2020/11/21/195100)
+ [用語まとめ](https://qiita.com/s059ff/items/f8127dc5e5b8cc15a4c3)
+ [conda-forgeについて](https://waregawa-log.hatenablog.com/entry/2019/01/08/070000)