【tensorflow C++】tensorflow1.8源码编译C++库包

        最近用了一些时间来研究C++版本的tensorflow 当然官网没有提供现成的库包,只能自己根据原码编译。网上翻了一遍,发现资料很多但都相对较为零散,这边记录一下自己编译库包(Release和Debug版本)的流程以及自己踩的坑。

电脑环境

  • win10
  • VS2019
  • cmake-3.20.1
  • swigwin-4.0.2
  • tensorflow-1.8.0
  • python3.6(Anaconda)

       编译时候会从git和一些国外网站在线下载一些依赖库包,所以提取要准备好高效上网的工具,否则一直处于time out状态。

CMAKE构建

        在tensorflow-1.8.0\tensorflow\contrib\cmake路径下创建一个build文件夹,作为vs工程的生成目录。

修改cmakeList.txt文件:

        找到 if (tensorflow_OPTIMIZE_FOR_NATIVE_ARCH)  的这一段代码,用下面的代码替换

 1 if (tensorflow_OPTIMIZE_FOR_NATIVE_ARCH)
 2   include(CheckCXXCompilerFlag)
 3   CHECK_CXX_COMPILER_FLAG("-march=native" COMPILER_OPT_ARCH_NATIVE_SUPPORTED)
 4   if (COMPILER_OPT_ARCH_NATIVE_SUPPORTED)
 5     set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -march=native")
 6   else()
 7     CHECK_CXX_COMPILER_FLAG("/arch:AVX" COMPILER_OPT_ARCH_AVX_SUPPORTED)
 8     if(COMPILER_OPT_ARCH_AVX_SUPPORTED)
 9       set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /arch:AVX")
10     endif()
11   endif()
12 endif()

        设置 option(tensorflow_ENABLE_GRPC_SUPPORT "Enable gRPC support" ON) , 将其中的 $ ON $ 修改为 $ OFF $ 。否则在编译的时候会报错,很麻烦。

        打开cmake GUI工具,将source code和build路径选择完成后,点击configure按钮,加载与项目相关的cmakeList.txt对应的配置。

 

 

        加载后报错,是由于未设置swig executable所导致。选中已下载的swig.exe文件路径并添加。

 

        对cmakeList.txt作如下配置,点击configure发现无报错,再点击generate生成vs项目文件。

         打开生成的vs项目tensorflow.sln文件,对整个工程项目并作如下配置。

        配置完成后,右键ALL_BUILD生成项目,此过程耗时比较长。在整个过程中,会出现各种问题,通常是因为网络问题,不能下载项目中需要的包,解决办法通常为启用高效上网工具,开启上网绿色通道。

        在编译过程中,可能遇到的问题有:

        1. 从GitHub上clone项目时候报【git early EOF】错误,导致项目生成失败。

        解决办法为:找到对应项目的cmake文件,并在其中写入  git config --global core.compression 0 

        如在生成protobuf项目时出现了如题所述错误,则在\tensorflow-1.8.0\tensorflow\contrib\cmake\build\protobuf\tmp路径下,找到protobuf-gitclone.cmake文件,并在其中添加代码:

1 execute_process(
2     COMMAND "C:/Program Files/Git/cmd/git.exe" config --global core.compression 0
3 )

        2.在编译过程中出现了OpenSSL SSL_connect: SSL_ERROR_SYSCALL in connection to github.com:443错误。

        解决办法同1所述,在对应项目的cmake文件中写入:

 

 

1 execute_process(
2     COMMAND "C:/Program Files/Git/cmd/git.exe" config --global --unset http.proxy
3     COMMAND "C:/Program Files/Git/cmd/git.exe" config --global --unset https.proxy
4 )

 

        3. Windows编译tensorflow时LINK : fatal error LNK1181: 无法打开输入文件“\pywrap_tensorflow_internal.lib错误。

        出现这个错误是因为_beam_search_ops、 _gru_ops 、_lstm_ops、 _nearest_neighbor_ops、 _periodic_resample_op这几个工程的配置属性有问题,由于修改方法是一样的,所以这里以_beam_search_ops为例进行说明。

        右键工程打开属性设置:

        在链接器 -> 常规 -> 附加库目录里加入

$(SolutionDir)$(Configuration);

        在链接器 -> 输入 -> 附件依赖项中将  \pywrap_tensorflow_internal.lib  ,修改为  pywrap_tensorflow_internal.lib 

        重新编译这几个工程,然后再重新编译ALL_BUILD。

        4. 若在编译过程中,遇到某些文件不能下载,或者下载路径不对的情况时,可以自行下载对应的文件放到 \tensorflow-1.8.0\tensorflow\contrib\cmake\build\downloads 路径下即可。如遇到eigen文件下载路径不存在的情况,则找到 tensorflow-1.8.0\tensorflow\contrib\cmake\build\eigen\src\eigen-stamp 路径下 download-eigen.cmake 文件,并将 "http://bitbucket.org/eigen/eigen/get/6913f0cf7d06.tar.gz" 替换为其镜像路径 "http://mirror.bazel.build/bitbucket.org/eigen/eigen/get/6913f0cf7d06.tar.gz" 即可(前提是需要高效上网的通路)。

提取安装包

        编译完成之后,最后的一步是从十几个G的编译结果中提取安装包(install).在build文件夹下执行如下命令:

 

1 release:
2 cmake.exe -DBUILD_TYPE=Release -P cmake_install.cmake 
3  
4 debug:
5 cmake.exe -DBUILD_TYPE=Debug-P cmake_install.cmake

 

        生成如下的安装文件

环境配置与常见问题

        【C++环境配置】

  • 右键项目属性>>配置属性>>VC++目录>>包含目录 && 库目录
  • 右键项目属性>>配置属性>>C/C++>>预处理器>>预处理器定义,输入COMPILER_MSVC 和 NOMINMAX(否则会报错:“(”:“::”右边的非法标记应输入标记符)
  • 右键项目属性>>配置属性>>链接器 >>附加依赖项,输入tensorflow.lib

 

        【Question】找不到tensorflow.dll
        【Solution】将已编译好的tensorflow的bin目录下 tensorflow.dll 复制到 debug/release目录下和*.exe一起

 

        【Question】error C2143: 语法错误: 缺少“;”(在“<”的前面)
                             error C4430: 缺少类型说明符 - 假定为 int。注意: C++ 不支持默认 int
                             error C2238: 意外的标记位于“;”之前
                             error C2039: "vector": 不是 "std" 的成员
        【Solution】std::vector<Item> items = std::vector<Item>();宣布一个完整类型。因此编译器需要知道声明std::vector在这一点上(除其他事项外,它必须建立在编译时评估常量sizeof xxx)。
                            解决办法是在xxx.h的标头#include <vector>,而不是的源文件中。

 

 

posted @ 2021-04-27 23:45  _再遇见  阅读(433)  评论(0编辑  收藏  举报