使用 Libdl.dlopen 杀死 Julia

Posted

技术标签:

【中文标题】使用 Libdl.dlopen 杀死 Julia【英文标题】:Using Libdl.dlopen kills Julia 【发布时间】:2018-03-03 13:52:04 【问题描述】:

我正在尝试从 Julia v0.6.2、Windows 10 调用 C 代码。

这是我用Cygwin gcc 编译成 DLL 的 C 代码。

int timesTwo(int x) 
    return 2*x;

编译命令:

gcc -c mydll.c
gcc -shared -o mydll.dll mydll.o

我用测试 C 程序测试了 DLL,它可以工作。然后我尝试使用 DLL 的绝对路径与 Julia 一起调用它。

using Base.Libdl
x = Int32(2)
mylib = dlopen("C:\\Users\\pedro\\Documents\\codigos\\exampleDLL\\C\\mydll.dll")
ccall((:timesTwo, mylib), Int32, (Int32,), x)

然后重新启动 Julia 的工作区(一旦我使用命令 dlopen,所有变量都将变为未定义)。

发生了什么,我该如何解决?


更新

那一定是windows的问题。无法在 Ubuntu 发行版中重现。

【问题讨论】:

也许您应该添加-fPIC 标志并重试。 int double( int x )... 甚至编译?!?! double is a reserved word. 实际函数名为ddouble。将其更改为 timesTwo 以避免歧义。 【参考方案1】:

我会尝试使用与 Julia 相同的编译器(带有 -fPIC 标志)来构建您的 DLL。在 Windows 上,Julia 实际上是用 Cygwin 到 MinGW 的交叉编译器:

https://github.com/JuliaLang/julia/blob/master/README.windows.md#cygwin-to-mingw-cross-compiling

您能否安装 mingw64-x86_64-gcc-core 包(仅用于 C 编译器)并使用 x86_64-w64-mingw32-gcc 编译器命令(而不是 gcc)?

【讨论】:

【参考方案2】:

使用-fPIC 开关生成与位置无关的代码。另外,您可能对Julia 撒谎,除非您的int 在特定平台上定义为int32。可以肯定的是,您需要将ccall((:timesTwo, mylib), Int32, (Int32,), x) 更改为ccall((:timesTwo, mylib), Cint, (Cint,), x)。最后,为了使代码适用于任何操作系统,请考虑将mylib = dlopen("C:\\Users\\pedro\\Documents\\codigos\\exampleDLL\\C\\mydll.dll") 替换为const mylib = dlopen(joinpath(pwd(), "mydll.dll"))const 是出于效率原因,joinpath 与操作系统无关,这意味着它将为基于 *nix 的系统添加正斜杠。稍后,当你想将库更改为.so 时,你也不应该处理斜线。

【讨论】:

以上是关于使用 Libdl.dlopen 杀死 Julia的主要内容,如果未能解决你的问题,请参考以下文章

如何杀死一个无法杀死的任务?

如何使用子进程模块杀死(或避免)僵尸进程

如何使用 C++ 以编程方式杀死进程?

如何杀死前台服务

《Linux学习并不难》进程管理:杀死进程之kill命令

使用Java杀死进程