我有一个 C++ 程序,我正尝试将其与 tensorflow C++ API 一起使用。我让它在 Linux 上运行良好。但是我无法在 Windows 上链接到愚蠢的东西。我正在使用 tensorflow 的 r2.0 分支。我正在使用 Visual C++ 2017 (v14.16.27023) 从源代码构建 tensorflow。花了一段时间,但我终于得到了 bazel 来构建 tensorflow_cc.dll 和 tensorflow_cc.lib。将我的程序链接到 tensorflow_cc.lib 最初给出了 3 个未定义的 tensorflow 符号
?_TensorShapeProto_default_instance_@tensorflow@@3VTensorShapeProtoDefaultTypeInternal@1@A
??0SessionOptions@tensorflow@@QEAA@XZ
?LoadSavedModel@tensorflow@@YA?AVStatus@1@AEBUSessionOptions@1@AEBVRunOptions@1@AEBV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@AEBV?$unordered_set@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@U?$hash@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@U?$equal_to@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@V?$allocator@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@@6@QEAUSavedModelBundle@1@@Z
我阅读了一些 github 错误报告,发现有一种复杂的方法用于将全局符号的子集导出到 .lib 文件中,该文件涉及 python 程序 tensorflow/tools/def_file_filter/def_file_filter.py.tpl 并且有人展示了如何在其中添加额外的符号以添加到导出的集合中。我继续这样做:
diff --git a/tensorflow/tools/def_file_filter/def_file_filter.py.tpl ...
@@ -154,6 +154,9 @@ def main():
else:
def_fp.write("\t" + decorated + " DATA\n")
taken.add(decorated)
+ def_fp.write("\t??0SessionOptions@tensorflow@@QEAA@XZ\n")
+ def_fp.write("\t?_TensorShapeProto_default_instance_@tensorflow@@3VTensorShapeProtoDefaultTypeInternal@1@A DATA\n")
+ def_fp.write("\t?LoadSavedModel@tensorflow@@YA?AVStatus@1@AEBUSessionOptions@1@AEBVRunOptions@1@AEBV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@AEBV?$unordered_set@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@U?$hash@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@U?$equal_to@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@V?$allocator@V?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@@6@QEAUSavedModelBundle@1@@Z\n")
def_fp.close()
exit_code = proc.wait()
然后我重新 bazeled tensorflow_cc.lib 并修复了三个中的两个。然后我发现链接上未定义的那个实际上已经导出了:
?_TensorShapeProto_default_instance_@tensorflow@@3VTensorShapeProtoDefaultTypeInternal@1@A
所以我实际上从对 def_file_filter.py.tpl 的更改中删除了它。该特定符号在从 .proto 文件生成的文件中定义到 bazel-out/x64_windows-opt/bin/tensorflow/core/framework/tensor_shape.pb.cc。它是一个全局范围的类实例:
static void InitDefaultsscc_info_TensorShapeProto_tensorflow_2fcore_2fframework_2ftensor_5fshape_2eproto() {
GOOGLE_PROTOBUF_VERIFY_VERSION;
{
void* ptr = &::tensorflow::_TensorShapeProto_default_instance_;
new (ptr) ::tensorflow::TensorShapeProto();
::PROTOBUF_NAMESPACE_ID::internal::OnShutdownDestroyMessage(ptr);
}
::tensorflow::TensorShapeProto::InitAsDefaultInstance();
}
我查看了tensorflow_cc.lib中的符号,确实找到了与这个符号相关的条目:
tensorflow_cc.dll:
0000000000000000 I .idata$4
0000000000000000 I .idata$5
0000000000000000 I .idata$6
U __IMPORT_DESCRIPTOR_tensorflow_cc
0000000000000000 I __imp_?_TensorShapeProto_default_instance_@tensorflow@@3VTensorShapeProtoDefaultTypeInternal@1@A
我不确定它是否正确。大概不是,因为我仍然得到:
link tfseg.dll .wsl.obj/plugin.obj .wsl.obj/segTask.obj .wsl.obj/tfseg....
Creating library C:/root/ispace/plugins/tfseg/bin_release/tfseg.lib and object C:/root/ispace/plugins/tfseg/bin_release/tfseg.exp
tfseg.obj : error LNK2001: unresolved external symbol "class tensorflow::TensorShapeProtoDefaultTypeInternal tensorflow::_TensorShapeProto_default_instance_" (?_TensorShapeProto_default_instance_@tensorflow@@3VTensorShapeProtoDefaultTypeInternal@1@A)
C:/root/ispace/plugins/tfseg/bin_release/tfseg.dll : fatal error LNK1120: 1 unresolved externals
我束手无策,非常沮丧。有人见过这个吗?有什么想法吗?
最佳答案
我能够解决此链接错误。很难看,我仍然觉得在 windows 上构建的 tensorflow 有很大问题。但如果其他人遇到同样的问题,这就是我所做的。我将包含缺失符号 (tensor_shape.pb.o) 的 .o 文件直接添加到我的链接行,这产生了一大堆未解析的符号,全部来自 google protobuf。然后我四处寻找并找到了一些 protobuf“.a”文件并将它们添加进去。奇迹般地,它起作用了。以下是新链接行的摘要:
cl.exe -MD ... plugin.obj .wsl.obj/segTask.obj .wsl.obj/tfseg.obj /link /dll ... c:/root/tensorflow/bazel-out/x64_windows-opt/bin/tensorflow/core/_objs/protos_all_proto_cc_impl/tensor_shape.pb.o c:/root/tensorflow/bazel-out/x64_windows-opt/bin/external/com_google_protobuf/libprotobuf.a c:/root/tensorflow/bazel-out/x64_windows-opt/bin/external/com_google_protobuf/libprotobuf_lite.a c:/root/tensorflow/bazel-bin/tensorflow/tensorflow_cc.lib
当时我能够成功使用 tensorflow,只需要 tensorflow_cc.dll 位于我的 LoadLibrary 搜索路径中。
关于c++ - 无法在 Windows 10/Visual C++ 2017 上使用 tensorflow C++ API tensorflow_cc.lib 链接 C++ -- undefined symbol r2.0,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58176287/