首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么在考虑到所有需要的库和引用时,我得到了对am `错误的“未定义的引用”?

为什么在考虑到所有需要的库和引用时,我得到了对am `错误的“未定义的引用”?
EN

Stack Overflow用户
提问于 2020-03-26 15:15:19
回答 1查看 197关注 0票数 1

本质上,我试图使用雷德兰rdf库,但我无法链接到它们。当我尝试使用redland库的一个简单的basic程序时,我会得到以下错误:

代码语言:javascript
复制
/usr/local/lib/librdf.a(rdf_init.o): In function `librdf_free_memory':
/home/ciaran/Software/redland/redland-1.0.17/src/rdf_init.c:671: undefined reference to `raptor_free_memory'
/usr/local/lib/librdf.a(rdf_init.o): In function `librdf_alloc_memory':
/home/ciaran/Software/redland/redland-1.0.17/src/rdf_init.c:689: undefined reference to `raptor_alloc_memory'
/usr/local/lib/librdf.a(rdf_init.o): In function `librdf_calloc_memory':
/home/ciaran/Software/redland/redland-1.0.17/src/rdf_init.c:707: undefined reference to `raptor_calloc_memory'

乍一看,您可能只是认为我缺少了一个链接库,这就是我在进一步检查之前所想的(请参阅下面),但是,所有的库都已经说明了。

在这种情况下,一个适当的最小工作示例是很困难的,因为它需要获取和构建我试图使用的库。但是,我已经创建了一个GitHub 存储库

代码语言:javascript
复制
$ git clone git@github.com:CiaranWelsh/RedlandBuildTest.git

它包含构建Redland库所需的源文件以及我使用的示例代码(这会中断)。

为了构建库,您还需要

代码语言:javascript
复制
    $ sudo apt install automake autoconf libtool gtk-doc-tools
    $ sudo apt install libxml2 libxml2-dev libxslt libxslt-dev libcurl4-openssl-dev libltdl-dev

注意,我正在开发用于Linux的windows子系统的Ubuntu-18.04。

为了获取、构建和安装库,我使用以下终端命令:

代码语言:javascript
复制
#raptor2
wget "http://download.librdf.org/source/raptor2-2.0.15.tar.gz" 
tar -xvf raptor2-2.0.15.tar.gz
cd raptor2-2.0.15
./autogen.sh 
make
sudo make install
代码语言:javascript
复制
# redland (librdf)
wget "http://download.librdf.org/source/redland-1.0.17.tar.gz" 
tar -xvf redland-1.0.17.tar.gz
cd redland-1.0.17 
./autogen.sh
make
sudo make install
代码语言:javascript
复制
# rasqal
wget "http://download.librdf.org/source/rasqal-0.9.33.tar.gz" 
tar -xvf rasqal-0.9.33.tar.gz
cd rasqal-0.9.33
./autogen.sh 
make 
sudo make install

它们作为shell脚本(get-raptor.shget-rasqal.shget-librdf.sh)在github存储库中可用。

以及我的最小CMake脚本(也在存储库中):

代码语言:javascript
复制
cmake_minimum_required(VERSION 3.15)
project(RedlandBuildTest)

set(CMAKE_CXX_STANDARD 14)

find_library(RAPTOR2_STATIC_LIBRARY
        NAMES libraptor2.a
        PATHS /usr/local/lib
        )

find_path(RAPTOR2_INCLUDE_DIR
        NAMES raptor2.h
        PATHS /usr/local/include/raptor2
        )
find_library(RASQAL_STATIC_LIBRARY
        NAMES librasqal.a
        PATHS /usr/local/lib
        )

find_path(RASQAL_INCLUDE_DIR
        NAMES rasqal.h
        PATHS /usr/local/include/rasqal
        )

find_library(LIBRDF_STATIC_LIBRARY
        NAMES librdf.a
        PATHS /usr/local/lib
        )

find_path(LIBRDF_INCLUDE_DIR
        NAMES librdf.h
        PATHS /usr/local/include
        )

add_executable(RedlandBuildTest main.c)

target_include_directories(RedlandBuildTest PRIVATE
        ${RAPTOR2_INCLUDE_DIR}
        ${RASQAL_INCLUDE_DIR}
        ${LIBRDF_INCLUDE_DIR}
        )

target_link_libraries(RedlandBuildTest PRIVATE
        ${RAPTOR2_STATIC_LIBRARY}
        ${RASQAL_STATIC_LIBRARY}
        ${LIBRDF_STATIC_LIBRARY}
        curl
        xml2
        xslt
        ltdl
        )

get_target_property(LINK_LIBRARIES RedlandBuildTest LINK_LIBRARIES)
get_target_property(INCLUDE_DIRECTORIES RedlandBuildTest INCLUDE_DIRECTORIES)

message(STATUS "

LINK_LIBRARIES      ${LINK_LIBRARIES}
INCLUDE_DIRECTORIES ${INCLUDE_DIRECTORIES}

")

message(STATUS "

    RAPTOR2_STATIC_LIBRARY   ${RAPTOR2_STATIC_LIBRARY}
    RAPTOR2_INCLUDE_DIR      ${RAPTOR2_INCLUDE_DIR}

    RASQAL_STATIC_LIBRARY    ${RASQAL_STATIC_LIBRARY}
    RASQAL_INCLUDE_DIR       ${RASQAL_INCLUDE_DIR}

    LIBRDF_STATIC_LIBRARY    ${LIBRDF_STATIC_LIBRARY}
    LIBRDF_INCLUDE_DIR       ${LIBRDF_INCLUDE_DIR}

")

以及CMake命令的输出:

代码语言:javascript
复制
#(looks good)
LINK_LIBRARIES      /usr/local/lib/libraptor2.a;/usr/local/lib/librasqal.a;/usr/local/lib/librdf.a;curl;xml2;xslt;ltdl 
INCLUDE_DIRECTORIES /usr/local/include/raptor2;/usr/local/include/rasqal;/usr/local/include


    RAPTOR2_STATIC_LIBRARY   /usr/local/lib/libraptor2.a
    RAPTOR2_INCLUDE_DIR      /usr/local/include/raptor2

    RASQAL_STATIC_LIBRARY    /usr/local/lib/librasqal.a
    RASQAL_INCLUDE_DIR       /usr/local/include/rasqal

    LIBRDF_STATIC_LIBRARY    /usr/local/lib/librdf.a
    LIBRDF_INCLUDE_DIR       /usr/local/include

为了进行构建,我使用了CLion,它只在后台执行以下操作:

代码语言:javascript
复制
mkdir build && cd build
CMake ..
make

这就给了我链接错误。通过使用nm检查Redland库的内容,我已经挖掘得更深了一点。

代码语言:javascript
复制
$nm -A librdf.a > librdf.a.nmoutput.txt
$nm -A libraptor2.a > libraptor2.a.nmoutput.txt
$nm -A librasqal.a > librasqal.a.nmoutput.txt 

第一次冒犯undfined reference错误

代码语言:javascript
复制
/usr/local/lib/librdf.a(rdf_init.o): In function `librdf_free_memory':
/home/ciaran/Software/redland/redland-1.0.17/src/rdf_init.c:671: undefined reference to `raptor_free_memory'

在函数librdf_free_memory中,它是在librdf.a中定义的引用。

代码语言:javascript
复制
# librdf.a.nmoutput.txt
...
librdf.a:rdf_init.o:0000000000000740 T librdf_free_memory
...

当我们查找对raptor_free_memory的未定义引用时,我们认为它在librdf.a.中确实是未定义的。

代码语言:javascript
复制
#librdf.a.nmoutput.txt
...
librdf.a:rdf_init.o:                 U raptor_free_memory
...

但是无论如何,这应该在libraptor2.a中,如果我们看一看,我们就会发现它确实存在,并且定义为它应该是的:

代码语言:javascript
复制
# libraptor2.a.nmoutput.txt
...
libraptor2.a:raptor_general.o:0000000000000863 T raptor_free_memory
...

我的理解是,链接的过程本质上应该用librdf.a内部的定义填充libraptor.a中未定义的引用,但这显然是没有发生的。

为什么会发生这种情况?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-03-26 15:25:25

当您的静态库相互依赖时,链接顺序关系到(参见响应)。

如果librdf依赖于libraptor库(如链接错误所指示的那样),那么当指定给链接器时,libraptor库应该在librdf之后列出。尝试根据库依赖关系重新排列target_link_libraries()命令中的库列表,以遵循此顺序。

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

https://stackoverflow.com/questions/60870437

复制
相关文章

相似问题

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