那些年走过的坑TF2.0-GPU安装

Tensorflow2.0-gpu 的安装的复杂早有耳闻,以前一直用的都是cpu版,一直通过conda一键安装,过于安逸。

哎,欠的账始终是要还的。

最近,接触到实验室服务器后,开始捣鼓Tensoflow2.0-GPU,才发现各种神坑。
首先因为学校服务器都是共享的无法获取root权限,导致无法更新显卡驱动,使得cuda10 ,无法安装。于是只能安装cuda9 。然后问题来了,google只提供了Tensorflow2.0-GPU cuda10的版本。通过Google发现有人也提了这个问题How to install tensorflow2.0 in cuda9? 。问题中的解决方案是 通过Tensoflow2.0的源码 在cuda9上重新编译就行了。因为Google提供的是基于cuda10编译的,并不能找到cuda9。

好了,有了解决方案本以为会很容易,结果又碰见权限问题。因为没有root权限,开始安装bazel编译工具时碰见了麻烦。记得以前看conda list时看见过bazel,于是Google了发现conda确实可绕过 root权限 进行bazel的安装 而且conda还会自动的帮你把bazel所需的 jdk一起安装,真的安逸。本以为会很顺利,结果编译了30分钟后,开始报错,提示该环境下没有找到keras-preprocessing ,keras-applications,numpy。(通过conda专门搭建的编译环境一时疏忽,只安装了bazel,别的都忘了安。)QAQ 白瞎了30分钟。

所有依赖的包安装好后,重新开始编译,32线程开工,花了大约1个小时。

配置

  • Ubuntu 16.04
  • GPU:Tesla M40(驱动387.26)
  • cuda 9.0
  • cudnn 7.6.0
  • conda

前期准备

CUDA、CUDNN安装

刚开始开始拿到服务器,居然连conda都没安,然后给服务器安上了conda。(conda一定要安, 后面可以通过conda绕过root权限)。

接下来就是根据GPU的驱动安装cuna和cudnn。 由于没有root权限 无法升级显卡驱动,只能安装对应驱动版本的cuda和cudnn。

显卡驱动版本可以通过nvidia-smi进行查看。

tf2_gpu安装1

至于cuda,cudnn怎么装,请自行参考google 或 baidu

特别强调 由于没有root权限 服务器/usr/local 路径下 一般用户无权修改 所以安装CUDA,CUDNN时请选择 当前用户的根目录进行安装。

有root权限的直接升级显卡驱动安装cuda10,从Tensorflow官方包进行安装。

根据显卡驱动 安装指定的 CUDA 版本 这里我用的是CUDA9.0版本。

安装CUDNN,需要英伟达账号,自己注册就行。 根据CUDA和显卡驱动 选择相应版本的CUDNN。

这里 建议CUDA9.0 的下载 CUDNN7.6.0版本,其余版本的CUDNN会有bug。

Download cuDNN v7.6.0 (May 20, 2019), for CUDA 9.0

CUDNN下载后 将其解压到CUDA目录下 即可。

解压后查看 path/cuda/lib64 路径下lib64文件是否完整。

1
2
3
# path 为你cuda的路径
cd path/cuda/lib64
ls -a

tf2_gpu安装3

安装后, 通过下方命令,查看是否安装成功。

1
2
# path 为你cuda的路径
cat path/cuda/include/cudnn.h | grep CUDNN_MAJOR -A 2

这里我安装在/disk1/lx 下所以 命令修改为:

1
cat /disk1/lx/cuda/include/cudnn.h | grep CUDNN_MAJOR -A 2

若显示下面信息,则代表成功安装CUDA和CUDNN。

1
2
3
4
5
6
7
8
9
(mk) wxy@sait:/disk1/lx/cuda$ cat /disk1/lx/cuda/include/cudnn.h | grep CUDNN_MAJOR -A 2
#define CUDNN_MAJOR 7
#define CUDNN_MINOR 6
#define CUDNN_PATCHLEVEL 0
--
#define CUDNN_VERSION (CUDNN_MAJOR * 1000 + CUDNN_MINOR * 100 + CUDNN_PATCHLEVEL)

#include "driver_types.h"
(mk) wxy@sait:/disk1/lx/cuda$

cuda,cudnn安装好后,就可以利用conda来创建 编译环境了。

Conda编译环境安装

1
conda create -n mk python=3.7

创建编译环境mk。

切换编译环境。

1
conda activate mk

在mk环境中,安装

  • pip
  • six
  • openjdk (Ubuntu16.x openjdk=8.X ; Ubuntu18.x openjdk=10.x )
  • numpy
  • wheel
  • setuptools
  • mock
  • future>=0.17.1
  • keras_applications==1.0.6
  • keras_preprocessing==1.0.5
1
2
3
conda install pip six openjdk numpy wheel setuptools mock future>=0.17.1
pip install keras_applications==1.0.6
pip install keras_preprocessing==1.0.5

可能keras_applications和keras_preprocessing 在conda中并没有,这时我们可以通过pip / conda进行安装。

开始就是这两个忘记安装了,导致白花30分钟QAQ。

Bazel环境安装

由于conda中提供的Bazel为0.26.1版本,而最新的TensorFlow2.1 则需求Bazel 0.29.1 ,所以我们需要安装相应的Bazel版本。

Bazel 0.29.1该链接中找到相应的安装包进行下载,这里我服务器安装的是Linux,所以下载对应的bazel-0.29.1-installer-linux-x86_64.sh

下载成功后,先给该.sh文件加上可执行权限。

1
chmod +x bazel-0.29.1-installer-linux-x86_64.sh

由于,我没有root权限,无法安装到系统usr文件夹中,所以要通过prefix改变安装路径。通过以下命令进行安装,将Bazel 安装到当前用户目录下的Bazel文件夹中。

1
./bazel-<version>-installer-linux-x86_64.sh --prefix=~/Bazel

安装后,在~/.bashrc中添加Bazel路径。

1
export PATH=$PATH:"~/Bazel/bin"

再对.bashrc 进行更新。

1
source ~/.bashrc

最后,我们通过,查看bazel 版本命令,判断是否安装成功。

1
bazel --version

若正确显示bazel 版本,则代表安装成功。

1
bazel 0.29.1

查看系统环境配置

1
cat ~/.bashrc

查看.bashrc 中是否有添加相关cuda 路径依赖。 这里的,所有路径参数,需要根据你安装的cuda路径进行修改。

1
2
3
4
5
export CUDA_HOME=/usr/local/cuda
export PATH=/usr/local/cuda/bin${PATH:+:${PATH}}
export LD_LIBRARY_PATH=/usr/local/cuda/lib64
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/cuda
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/cuda/extras/CUPTI/lib64

克隆TensorFlow代码库

1
2
git clone https://github.com/tensorflow/tensorflow.git
cd tensorflow

由于代码库默认的分支为master。通过,下面代码进行分支切换。

1
git checkout r2.0   #要编译的是tf2.0 所以切换到r2.0 版本

配置编译相关参数

启动编译配置,输入accept后,开始进行配置,根据需求输入y/n 就行,一般只有CUDA那输入y,其余默认回车就行

1
./configure

在configure中,会得到下方显示,重要的就只有cuda 那里输入Y

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
(mk) wxy@sait:/disk1/lx/tf2/tensorflow$ ./configure 
WARNING: --batch mode is deprecated. Please instead explicitly shut down your Bazel server using the command "bazel shutdown".
You have bazel 0.24.1- (@non-git) installed.
Please specify the location of python. [Default is /disk1/lx/conda/envs/mk/bin/python]:


Found possible Python library paths:
/disk1/lx/conda/envs/mk/lib/python3.7/site-packages
Please input the desired Python library path to use. Default is [/disk1/lx/conda/envs/mk/lib/python3.7/site-packages]

Do you wish to build TensorFlow with XLA JIT support? [Y/n]: n
No XLA JIT support will be enabled for TensorFlow.

Do you wish to build TensorFlow with OpenCL SYCL support? [y/N]: n
No OpenCL SYCL support will be enabled for TensorFlow.

Do you wish to build TensorFlow with ROCm support? [y/N]: n
No ROCm support will be enabled for TensorFlow.

Do you wish to build TensorFlow with CUDA support? [y/N]: y
CUDA support will be enabled for TensorFlow.

Do you wish to build TensorFlow with TensorRT support? [y/N]: n
No TensorRT support will be enabled for TensorFlow.

Found CUDA 9.0 in:
/usr/local/cuda/lib64
/usr/local/cuda/include
Found cuDNN 7 in:
/usr/local/cuda/lib64
/usr/local/cuda/include


Please specify a list of comma-separated CUDA compute capabilities you want to build with.
You can find the compute capability of your device at: https://developer.nvidia.com/cuda-gpus.
Please note that each additional compute capability significantly increases your build time and binary size, and that TensorFlow only supports compute capabilities >= 3.5 [Default is: 5.2,5.2]:


Do you want to use clang as CUDA compiler? [y/N]: n
nvcc will be used as CUDA compiler.

Please specify which gcc should be used by nvcc as the host compiler. [Default is /usr/bin/gcc]:


Do you wish to build TensorFlow with MPI support? [y/N]: n
No MPI support will be enabled for TensorFlow.

Please specify optimization flags to use during compilation when bazel option "--config=opt" is specified [Default is -march=native -Wno-sign-compare]:


Would you like to interactively configure ./WORKSPACE for Android builds? [y/N]: n
Not configuring the WORKSPACE for Android builds.

Preconfigured Bazel build configs. You can use any of the below by adding "--config=<>" to your build command. See .bazelrc for more details.
--config=mkl # Build with MKL support.
--config=monolithic # Config for mostly static monolithic build.
--config=gdr # Build with GDR support.
--config=verbs # Build with libverbs support.
--config=ngraph # Build with Intel nGraph support.
--config=numa # Build with NUMA support.
--config=dynamic_kernels # (Experimental) Build kernels into separate shared objects.
--config=v2 # Build TensorFlow 2.x instead of 1.x.
Preconfigured Bazel build configs to DISABLE default on features:
--config=noaws # Disable AWS S3 filesystem support.
--config=nogcp # Disable GCP support.
--config=nohdfs # Disable HDFS support.
--config=noignite # Disable Apache Ignite support.
--config=nokafka # Disable Apache Kafka support.
--config=nonccl # Disable NVIDIA NCCL support.
Configuration finished
(mk) wxy@sait:/disk1/lx/tf2/tensorflow$

由于实验室服务器是共享,有别的用户开始在usr/local 下安装过cuda 导致编译程序会自动优先默认识别usr/local目录下的cuda。但由于每个用户安装的cuda版本不同,并且又没有权限去修改usr/local下cuda的指向,我们可以在配置好configure后,在tensorflow目录下会产生 .tf_configure.bazelrc

通过下面命令 查看 .tf_configure.bazelrc 中生成的cuda 路径是否正确,若不正确,就对其进行修改。

1
vim .tf_configure.bazelrc
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
wxy@sait:/disk1/lx/tf2/tensorflow$ cat .tf_configure.bazelrc 
build --action_env PYTHON_BIN_PATH="/disk1/lx/conda/envs/mk/bin/python"
build --action_env PYTHON_LIB_PATH="/disk1/lx/conda/envs/mk/lib/python3.7/site-packages"
build --python_path="/disk1/lx/conda/envs/mk/bin/python"
build:xla --define with_xla_support=true
build --action_env CUDA_TOOLKIT_PATH="/usr/local/cuda"
build --action_env TF_CUDA_COMPUTE_CAPABILITIES="5.2,5.2"
build --action_env LD_LIBRARY_PATH=":/usr/local/cuda/lib64"
build --action_env GCC_HOST_COMPILER_PATH="/usr/bin/gcc"
build --config=cuda
build:opt --copt=-march=native
build:opt --copt=-Wno-sign-compare
build:opt --host_copt=-march=native
build:opt --define with_default_optimizations=true
test --flaky_test_attempts=3
test --test_size_filters=small,medium
test --test_tag_filters=-benchmark-test,-no_oss,-oss_serial
test --build_tag_filters=-benchmark-test,-no_oss
test --test_tag_filters=-gpu
test --build_tag_filters=-gpu
build --action_env TF_CONFIGURE_IOS="0"

重点关注下面两行,判断路径是否正确,如不正确,可以自己修改到指定位置。

1
2
build --action_env CUDA_TOOLKIT_PATH="/usr/local/cuda"
build --action_env LD_LIBRARY_PATH="/usr/local/cuda/lib64"

如果你的cuda安装在默认位置 则跳过修改该文件。否则,对 .tf_configure.bazelrc 文件进行修改。

.tf_configure.bazelrc 文件中的cuda指定到 特定cuda版本的位置即可

比如我,需要配置指定位置的cuda,就可以如下修改。

值得注意的是 LD_LIBRARY_PATH 是根据你 .bashrc 中的路径自动生成的。

1
2
3
build --action_env CUDA_TOOLKIT_PATH="/disk1/lx/cuda"
build --action_env LD_LIBRARY_PATH="/disk1/lx/cuda/lib64:/disk1/lx/cuda/lib64:/disk1/lx/cuda/lib64:/disk1/lx/cuda/lib64:/disk1/lx/cuda:/disk1/lx/cuda/extras/CUPTI/lib64"

Bazel build

编译前,最好执行下面的 bazel清空命令,清除下bazel的缓存,以免报错

1
bazel clean --expunge

一切准备就绪,就可以开始编译了。编译有两种,一种是仅支持cpu,另一种是支持gpu,需要哪个就用那个命令。

仅支持 CPU

1
bazel build --config=opt //tensorflow/tools/pip_package:build_pip_package

GPU 支持

这里我们要用的是GPU,所以输入下面 命令就可以开始编译了。

1
bazel build --config=opt --config=cuda //tensorflow/tools/pip_package:build_pip_package

编译前一定要通过conda list,pip list 来查看 前期准备 中 提到的依赖包是否全部安装。

服务器32线程全开,经过漫长一个小时等待,终于编译完成了QAQ。

编译完成后会创建一个名为 build_pip_package 的可执行文件

再通过下面命令进行编译,编译后会在/disk1/lx下产生一个.whl的软件包。

该命令后面可以指定.whl文件存放的位置。 这里默认保存在当前文件夹中。

1
./bazel-bin/tensorflow/tools/pip_package/build_pip_package ./   

比如我要将.whl存放到路径/disk1/lx下, 就可以如下进行修改:

1
./bazel-bin/tensorflow/tools/pip_package/build_pip_package /disk1/lx

pip 安装

得到了.whl文件后

通过pip执行安装

1
pip install tensorflow-2.0.0-cp37-cp37m-linux_x86_64.whl 

python环境测试

1
2
3
4
5
import tensorflow as tf
print(tf.__versiong__)
print(tf.test.is_gpu_available())


tf2_gpu安装2

看见True 就代表成功了。

然后,通过pycharm远程连接操作,真的方便。

看见True,当时感动哭了,花了两天终于把这环境在服务器上配置好了。

两天前,还傻到去找老师要root账号,去升级显卡驱动。结果,被老师回绝了,QAQ。

凡事还是只能靠自己。

彩蛋

编译好的Tensorflow2.X-GPU-CUDA9.0 可以配合conda安装的CUDA 使用。

Tensorflow2.X-GPU-CUDA9.0

如果需要帮助,请在下方留言。