環境說明
ubuntu16.04
cuda10.0
2080Ti顯卡
拉取代碼和修改編譯腳本
拉取代碼
用戶先clone代碼:
git clone https://github.com/torch/distro.git ~/torch --recursive
通常下載很慢,--recursive參數下載的submodule會失敗,需要多執行幾次如下命令:
cd torch
git submodule update --init --recursive
安裝依賴
1.torch源碼中明確指定的依賴
需要sudo權限安裝,如果當前賬戶不是sudo賬戶也不是root賬戶則需要聯系你的管理員來安裝:
bash install-deps;
2.torch源碼沒說,但實測下來需要的依賴
使用原生的lua5.2而不是luajit,需要apt裝一下lua:
sudo apt install lua5.2
配置cuda/cudnn:系統管理員先前已經安裝了cuda-8.0, cuda-9.0, cuda-10.0到/usr/local/cuda-10.0等目錄,在~/.bashrc中配置PATH和LD_LIBRARY_PATH即可。
配置CMake,需要高版本cmake,ubuntu16.04用apt裝的cmake3.5.1版本太老,FindCUDA.cmake相關有問題。
-
手動安裝了cmake-3.15-rc1
-
拷貝CMake-3.15-rc1安裝路徑下的Modules目錄到~/torch/cmake/3.15/
-
拷貝~/torch/cmake/3.6/CMakeLists.txt到~/torch/cmake/3.15目錄
-
配置使用CUDA10,因為用的是2080Ti,cuda9.0雖然能找到
compute_75
算力但是編譯失敗,需要配置cuda10。編輯~/.bashrc添加:
export CUDA_HOME=/usr/local/cuda-10.0
export PATH=/usr/local/cmake-3.15/bin:/usr/local/cuda-10.0/bin:$PATH
export LD_LIBRARY_PATH=/usr/local/cuda-10.0/lib64
export TORCH_NVCC_FLAGS="-Xcompiler -D__CUDA_NO_HALF_OPERATORS__"
- cudnn也需要一定的配置。torch7默認用cudnn5,cuda10搭配的cudnn7.5。
git clone https://github.com/soumith/cudnn.torch.git -b R7 && cd cudnn.torch && luarocks make cudnn-scm-1.rockspec
(from: https://github.com/soumith/cudnn.torch/issues/383)
然后~/.bashrc配置:
export CUDNN_PATH="/usr/local/cuda-10.0/lib64/libcudnn.so.7"
3.torch源碼修改
幾個坑:
- torch官方很久不更新了,ATen等C++重新實現的核心代碼在PyTorch官方repo中,https://github.com/torch/torch7 則幾乎不維護
- torch7不支持cuda10.0,需要自行修改cmake腳本
- torch7判斷cuda>=7.0.5就使用FP16,然而我這里用的gcc-5.4發現FP16(half精度)相關的代碼報錯,需要手動注釋掉,修改包括cmake腳本和.cuh、.c代碼
具體包括:
因為torch默認不支持cuda10.0,需要修改extra/cutorch/lib/THC/cmake/select_compute_arch.cmake
:
找到
list(APPEND CUDA_COMMON_GPU_ARCHITECTURES "6.0" "6.1" "6.1+PTX"
改為
list(APPEND CUDA_COMMON_GPU_ARCHITECTURES "6.0" "6.1" "6.1+PTX" "7.5")
找到
if(nvcc_res EQUAL 0)
# only keep the last line of nvcc_out
STRING(REGEX REPLACE ";" "\\\\;" nvcc_out "${nvcc_out}")
STRING(REGEX REPLACE "\n" ";" nvcc_out "${nvcc_out}")
list(GET nvcc_out -1 nvcc_out)
string(REPLACE "2.1" "2.1(2.0)" nvcc_out "${nvcc_out}")
set(CUDA_GPU_DETECT_OUTPUT ${nvcc_out} CACHE INTERNAL "Returned GPU architetures from detect_gpus tool" FORCE)
endif()
修改為:
#if(nvcc_res EQUAL 0)
# # only keep the last line of nvcc_out
# STRING(REGEX REPLACE ";" "\\\\;" nvcc_out "${nvcc_out}")
# STRING(REGEX REPLACE "\n" ";" nvcc_out "${nvcc_out}")
# list(GET nvcc_out -1 nvcc_out)
# string(REPLACE "2.1" "2.1(2.0)" nvcc_out "${nvcc_out}")
# set(CUDA_GPU_DETECT_OUTPUT ${nvcc_out} CACHE INTERNAL "Returned GPU architetures from detect_gpus tool" FORCE)
#endif()
set(__nvcc_out "7.5")
修改torch/install.sh,把里面所有3.6改成3.15。
去掉FP16功能相關的宏,因為編譯會失敗。方法:
ag 'CUDA_HAS_FP16'
找到
extra/cutorch/lib/THC/CMakeLists.txt
extra/cutorch/CMakeLists.txt
這兩個文件,里面FLAGS去掉CUDA_HAS_FP16相關功能。
extra/cutorch/lib/THC/THCHalf.h,去掉#define CUDA_HAS_FP16 1
extra/cutorch/lib/THC/THCTensorMode.cuh,找到帶
extra/cutorch/lib/THC/THCGeneral.c,文件最后面兩個函數half2float和float2half,用#ifdef CUDA_HAS_FP16 #endif包裹
error: cannot overload functions distinguished by return type alone
需要添加nvcc的flags,vim ~/torch/extra/cutorch/lib/THC/CMakeLists.txt +65
,添加:
-Xcompiler -D__CORRECT_ISO_CPP11_MATH_H_PROTO
error: more than one operator "==" matches these operands
原因是cuda和torch的頭文件都提供了相同的重載運算符,編譯器不知道用哪一個。輸入下面shell命令禁止使用cuda的頭文件編譯torch即可:
export TORCH_NVCC_FLAGS="-D__CUDA_NO_HALF_OPERATORS__"
然后重新執行torch的編譯安裝
(from: https://blog.csdn.net/u013066730/article/details/80936627)
編譯
TORCH_LUA_VERSION=LUA52 ./install.sh 2>&1 |
編譯失敗,清理辦法
./clean.sh
編譯成功,截圖: