从C中调用Java的Haskell

编程入门 行业动态 更新时间:2024-10-09 02:25:15
本文介绍了从C中调用Java的Haskell的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧! 问题描述 这可能听起来像一场噩梦,但我真的想让这个工作。我大部分都使用这个例子:从Haskell调用C ,并试图在ubuntu上运行。 p>

我在java中运行它:

package test; public class JniTest { public native int fib(int x); }

在使用javah创建.h文件之后,在c中:(test_JniTest.c )

#includetest_JniTest.h #includeSafe_stub.h JNIEXPORT jint JNICALL Java_test_JniTest_fib(JNIEnv * e,jobject o,jint f) { return fibonacci_hs(f); $ / code>

然后在haskell(存根前)中引用:(Safe.hs)

模块安全其中 导入Foreign.C.Types 斐波纳契:: Int - > Int fibonacci n = fibs !! n 其中fibs = 0:1:zipWith(+)fibs(尾纤) fibonacci_hs :: CInt - > CInt fibonacci_hs = fromIntegral。斐波纳契。 fromIntegral 国外出口ccall fibonacci_hs :: CInt - > CInt

这就是我想要编译它的内容:

ghc -c -O Safe.hs

后跟:

GHC -shared -o libTest.jnilib -optc-O test_JniTest.c -I / usr / lib中/ JVM / JAVA -6-sun-1.6.0.26 / include -I / usr / lib / jvm / java-6-sun-1.6.0.26 / include / linux

和我收到此错误:

在/ usr / bin中/ LD:test_JniTest.o:搬迁对$ b R_X86_64_PC32 $ b未定义符号`fibonacci_hs'在制作共享的对象时不能使用;使用-fPIC / usr / bin / ld重新编译:最终链接失败:错误值 collect2:ld返回1退出状态

我不是任何方式的专家,也不知道该怎么做。我尝试用-fPIC编译各种不同的方式,但我一直在得到相同的错误。任何想法,我可能做错了什么?

谢谢!

解决方案

尽管我已经在这里回答了这个问题: Java与Haskell之间的通信,因为这个问题更多的是关于错误本身,所以我会在这里添加细节。这个问题源于Haskell不是很好地支持共享库,而Java需要它们。 建筑物插件与Haskell共享库为我们提供了这种见解和解决方法:

原则上,您可以在链接步骤中使用没有-dynamic的-shared。这意味着将所有基础库的静态链接到新的共享库中。这将会形成一个非常大但独立的共享库。然而,这将需要所有的静态库都使用-fPIC构建,以便代码适合包含到共享库中,而我们目前不这样做。

如果我们再次使用ldd来查看我们所做的libfoo.so,我们会注意到它缺少对rts库的依赖。这是我们尚未解决的问题,所以目前我们可以自己添加依赖项:

$ ghc --make -dynamic -fPIC -shared -o Foo.hs \ libfoo.so -lHSrts-ghc6.11 -optl-WL,-rpath为/ opt / GHC / lib中/ ghc6.11 /

这是一种解决方法,因为它要求我们知道rts的版本图书馆在建设时间。

This probably sounds like a nightmare, but I'd really like to get this working. I am using this example for the most part: Calling C from Haskell and am trying to get this working on ubuntu.

I am running this in java:

package test; public class JniTest { public native int fib(int x); }

this in c after creating the .h file with javah: (test_JniTest.c)

#include "test_JniTest.h" #include "Safe_stub.h" JNIEXPORT jint JNICALL Java_test_JniTest_fib(JNIEnv * e, jobject o, jint f) { return fibonacci_hs(f); }

and then for reference in haskell (before stub): (Safe.hs)

module Safe where import Foreign.C.Types fibonacci :: Int -> Int fibonacci n = fibs !! n where fibs = 0 : 1 : zipWith (+) fibs (tail fibs) fibonacci_hs :: CInt -> CInt fibonacci_hs = fromIntegral . fibonacci . fromIntegral foreign export ccall fibonacci_hs :: CInt -> CInt

and this is what i'm trying to compile it with:

ghc -c -O Safe.hs

followed by:

ghc -shared -o libTest.jnilib -optc-O test_JniTest.c -I/usr/lib/jvm/java-6-sun-1.6.0.26/include -I/usr/lib/jvm/java-6-sun-1.6.0.26/include/linux

and I am getting this error:

/usr/bin/ld: test_JniTest.o: relocation R_X86_64_PC32 against undefined symbol `fibonacci_hs' can not be used when making a shared object; recompile with -fPIC /usr/bin/ld: final link failed: Bad value collect2: ld returned 1 exit status

I am not a c expert by any means and have no idea what to do about this. I tried compiling various ways with -fPIC, but I kept on getting the same error. Any idea what I might be doing wrong?

Thanks!

解决方案

Although I've pretty much answered this question here: Communication between Java and Haskell, since this issue is more about the error itself, I will be adding the details for that here. The issue stems from Haskell not supporting shared libraries very well, while Java requires them. Buildings plugins as Haskell shared libs gives us this insight and workaround:

In principle you can use -shared without -dynamic in the link step. That would mean to statically link the rts all the base libraries into your new shared library. This would make a very big, but standalone shared library. However that would require all the static libraries to have been built with -fPIC so that the code is suitable to include into a shared library and we don't do that at the moment.

If we use ldd again to look at the libfoo.so that we've made we will notice that it is missing a dependency on the rts library. This is problem that we've yet to sort out, so for the moment we can just add the dependency ourselves:

$ ghc --make -dynamic -shared -fPIC Foo.hs -o libfoo.so \ -lHSrts-ghc6.11 -optl-Wl,-rpath,/opt/ghc/lib/ghc-6.11/

This is a workaround because it requires us to know the version of the rts library at build time.

更多推荐

从C中调用Java的Haskell

本文发布于:2023-11-28 17:56:31,感谢您对本站的认可!
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:Java   Haskell

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!