首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >将ocaml for windows与外部c库连接时出现链接错误

将ocaml for windows与外部c库连接时出现链接错误
EN

Stack Overflow用户
提问于 2017-03-08 03:09:42
回答 1查看 349关注 0票数 1

我正在用ocaml开发一个项目,它需要我将它与OGDF外部c++库接口。这一切都在我的mac上运行,但现在我正试图使用Ocaml for windows (https://fdopen.github.io/opam-repository-mingw/),即MinGW Cygwin的Ocaml port创建一个Windows版本。在这个版本中,我可以将ocaml与C代码接口,它工作得很好,但只要我尝试在C代码中包含一个外部库,我就会收到来自链接器错误,在本例中是flexdll (https://github.com/alainfrisch/flexdll)。链接器说它无法在整个库中解析_Unwind_Resume和__emutls_get_address的符号。

下面是一个玩具示例:

我的.ml文件t.ml:

代码语言:javascript
复制
external print : unit -> unit = "print"

let () =
  Printf.printf "platform: %s\n" (Sys.os_type);
  print ()

我的.cpp文件tc.cpp:

代码语言:javascript
复制
#include <stdio.h>
#include "caml/mlvalues.h"
#define CAML_NAME_SPACE
//#include <ogdf/basic/Graph.h>

extern "C" value print(value unused) {
  printf("hello from C\n");
  return Val_unit;  
}  

我的makefile:

代码语言:javascript
复制
t.exe: t.ml tc.o 
    ocamlopt -verbose  -ccopt -pthread  \
    -cclib -lstdc++ -w s   \
    -ccopt -L../cdeg/ogdf/_release \
    -cclib -lOGDF \
    tc.o t.ml \
    -o t.exe

tc.o: tc.cpp
    x86_64-w64-mingw32-gcc  -c \
     -march=x86-64 -mtune=generic -O2 -mms-bitfields -Wall -Wno-unused \
    tc.cpp \
    -I../cdeg/ogdf  -L../cdeg/ogdf/_release -lOGDF \
    -I ~/.opam/4.04.0+mingw64c/lib/ocaml \
    -lstdc++   -pthread  -o tc.o

就像这样,它可以顺利地编译,但是如果我在tc.cpp中取消对ogdf include行的注释,我会得到以下输出:

代码语言:javascript
复制
$ make
x86_64-w64-mingw32-gcc  -c \
 -march=x86-64 -mtune=generic -O2 -mms-bitfields -Wall -Wno-unused \
tc.cpp \
-I../cdeg/ogdf  -L../cdeg/ogdf/_release -lOGDF \
-I ~/.opam/4.04.0+mingw64c/lib/ocaml \
-lstdc++   -pthread  -o tc.o
ocamlopt -verbose  -ccopt -pthread  \
-cclib -lstdc++ -w s   \
-ccopt -L../cdeg/ogdf/_release \
-cclib -lOGDF \
tc.o t.ml \
-o t.exe
+ x86_64-w64-mingw32-as -o "t.o" "C:\OCaml64\tmp\camlasme5f9bd.s"
+ x86_64-w64-mingw32-as -o "C:\OCaml64\tmp\camlstartupf2b3f1.o" "C:\OCaml64\tmp\camlstartup101e51.s"
+ flexlink -chain mingw64 -stack 33554432 -exe -o "t.exe"   "-LC:/OCaml64/home/Nathaniel.Miller/.opam/4.04.0+mingw64c/lib/ocaml" -pthread -L../cdeg/ogdf/_release "C:\OCaml64\tmp\camlstartupf2b3f1.o" "C:/OCaml64/home/Nathaniel.Miller/.opam/4.04.0+mingw64c/lib/ocaml\std_exit.o" "t.o" "C:/OCaml64/home/Nathaniel.Miller/.opam/4.04.0+mingw64c/lib/ocaml\stdlib.a" "-lstdc++" "-lOGDF" "tc.o" "C:/OCaml64/home/Nathaniel.Miller/.opam/4.04.0+mingw64c/lib/ocaml\libasmrun.a" -lws2_32
** Cannot resolve symbols for ../cdeg/ogdf/_release\libOGDF.a(PoolMemoryAllocator.o/
PreprocessorLayout.o/
extended_graph_alg.o/
graph_generators.o/
random_hierarchy.o/
simple_graph_alg.o/
CPlanarEdgeInserter.o/

... [a bunch of other .o files from the library]...

UpwardPlanarModule.o/
UpwardPlanarSubgraphModule.o/
UpwardPlanarSubgraphSimple.o/
VisibilityLayout.o/
):
 _Unwind_Resume
 __emutls_get_address
** Cannot resolve symbols for ../cdeg/ogdf/_release\libOGDF.a(basic.o):
 _Unwind_Resume
File "caml_startup", line 1:
Error: Error during linking
make: *** [makefile:20: t.exe] Error 2

如果我不将它连接到ocaml,而是向t.c添加一个main()函数,那么它在包含外部库的x86_64-w64-mingw32-gcc下编译得很好。我尝试过包含一些其他的小型外部库,但它们并没有导致这个问题。

我的第一个想法是,问题可能与链接文件的编译方式不同有关,但我使用ocamlopt -configure提供的编译器和选项编译库和.cpp文件。如果它们都不是以相同的方式编译的,我就不会期望能够让tc.cpp分别与ocamlopt和外部库一起工作,但只有当我尝试使用这两者时才会得到错误。那么,这是Ocaml for windows或flexdll的问题,还是我安装其中一个的问题?我不知道下一步该尝试什么,任何想法、建议和/或对这里发生的事情的解释都将非常感谢。

EN

回答 1

Stack Overflow用户

发布于 2017-03-11 06:07:44

我有一个部分的答案。不知何故,这个问题来自flexdll。我改用Cygwin版本的ocaml和gcc,仍然有同样的问题。然后我重新编译了配置了-no-shared libs标志的ocaml,它使ocamlopt链接到了gcc而不是flexdll,现在一切都编译好了。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/42656356

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档