在R包中构建和链接共享库 - 代码编译,链接,但不会加载

时间:2015-07-31 16:07:18

标签: c++ linux r rcpp

平台测试:Linux Mint 17,Ubuntu 14.04 完整示例:this repository

我在做什么以及为什么?

我尝试使用CAF libraryRcpp构建一个包裹RcppEigen子集的R包。

我已成功将R包链接到CAF example here的系统级安装(注意:ABSEIR不再使用CAF,2015年2月5日),但我&# 39;想要有一个很好的方法将CAF部署到没有管理员访问权限的机器上,从而简化了其他CAF相关软件包的安装(是的,我知道R不直接支持链接其他已编译的软件包,但似乎其他人已经成功绕过了这个限制)。

问题是什么?

除了包共享对象(RcppCAF.so)之外,我还在包编译期间构建了两个共享对象:libcaf_core.so和libcaf_io.so。这些已成功编译和链接,但程序包无法加载,声称:

** testing if installed package can be loaded
Error in dyn.load(file, DLLpath = DLLpath, ...) : 
  unable to load shared object '/home/grantbrown/R/x86_64-pc-linux-gnu-library/3.2/RcppCAF/libs/RcppCAF.so':
  librcaf_core.so: cannot open shared object file: No such file or directory

我尝试了什么?

除了众多失败的Makevars配置外,我还发现了这一点 如果我手动将LD_LIBRARY_PATH设置为包含已编译代码的文件夹,则该包将成功安装。显然,我想通过找到一种方法来告诉R在哪里寻找这些依赖关系来避免这一步骤。为此,我试图使用 inst 文件夹无效。我的Makevars文件如下:

ROOT_DIR := $(abspath .)                                                        
$(info The compilation root directory is: $(ROOT_DIR))                          
$(info The name of the shared library to be created is: $(SHLIB))               
$(info The place R should look for librcaf_core.so is: $(abspath ./libcaf_core)) 
$(info The place R should look for librcaf_io.so is: $(abspath ./libcaf_io)) 

SOURCES = $(wildcard ./*.cpp)
SOURCES1 = $(wildcard ./libcaf_core/*.cpp)
SOURCES2 = $(wildcard ./libcaf_io/*.cpp)

OBJECTS = $(SOURCES:.cpp=.o)
OBJECTS1 = $(SOURCES1:.cpp=.o)
OBJECTS2 = $(SOURCES2:.cpp=.o)

PKG_CPPFLAGS+= -std=c++11 -Dlibcaf_core_shared_EXPORTS -Wall -pedantic -pthread -fPIC -O2 -g -fPIC -I../inst -I../inst/libcaf_core -I../inst/libcaf_io 

PKG_LIBS += -L$(abspath ./libcaf_core) -lrcaf_core -L$(abspath ./libcaf_io) -lrcaf_io

all: $(SHLIB) 

$(SHLIB): $(OBJECTS) libcaf_core/librcaf_core.so libcaf_io/librcaf_io.so

libcaf_core/librcaf_core.so: $(OBJECTS1)
    g++ -o libcaf_core/librcaf_core.so $(OBJECTS1) $(PKG_CPPFLAGS) -shared

libcaf_io/librcaf_io.so: $(OBJECTS2) 
    g++ -o libcaf_io/librcaf_io.so $(OBJECTS2) $(PKG_CPPFLAGS) -shared

StackOverflow和邮件列表上有很多线程可以处理加载共享对象的问题,但我找不到任何具有完全相同问题的人。我甚至在过去做过类似的事情而没有任何问题,所以我很难弄清楚为什么R无法找到我的共享对象。有什么建议吗?

修改

Dirk建议编译一个共享对象,我现在正在研究它。在"使用Makevars"但是,它似乎意味着建立依赖关系应该是可能的:

"如果要创建然后链接到库,比如使用子目录中的代码,请使用类似

的内容
.PHONY: all mylibs

all: $(SHLIB)
$(SHLIB): mylibs

mylibs:
    (cd subdir; make)

"

1 个答案:

答案 0 :(得分:1)

The easiest approach, which you also seem to have found as per your most recent commit is to just have R 'glue' all object code into a single shared library.

That tends to "just work" but it is a little costly as the library needs to be rebuilt. We could look into packaging CAF as an external library which would make RcppCAF more lightweight.