【问题标题】:c++ cmake/make: linker ld does not find library (missing path?)c++ cmake/make:链接器 ld 找不到库(缺少路径?)
【发布时间】:2014-06-30 20:05:32
【问题描述】:

我目前正在努力链接一个需要与 GLFW3 链接的 C++ 项目,即使用 -lglfw3 调用 ld。问题是这以前有效,现在我不知道为什么不再有效了。

sudo  pkg-config --libs glfw3 
-L/usr/local/lib -lglfw3  

该库也存在于上述声明所打印的特定位置。但是,ld 说:

Linking CXX executable modeling_2014_framework
/usr/bin/ld: error: cannot find -lglfw3
CMakeFiles/modeling_2014_framework.dir/main.cpp.o:main.cpp:function init(): error: undefined reference to 'glfwInit'
...
collect2: error: ld returned 1 exit status
make[2]: *** [modeling_2014_framework] Error 1
make[1]: *** [CMakeFiles/modeling_2014_framework.dir/all] Error 2
make: *** [all] Error 2

我正在使用 cmake 来创建 makefile。这就是 CMakeLists 的样子:

cmake_minimum_required (VERSION 2.8)

set (project_name modeling_2014_framework)

# create project
project (${project_name})

# sources
set(SOURCES main.cpp)

# add headers to the project
file(GLOB MY_HEADERS "src/*.h")
list(APPEND HEADERS ${MY_HEADERS})

# add sources to the project
file(GLOB MY_SOURCES "src/*.cpp")
list(APPEND SOURCES ${MY_SOURCES})

# i also tried to manually set them here, which however also does not help
#set(CMAKE_LIBRARY_PATH ${CMAKE_LIBRARY_PATH} /usr/local/lib)

# OpenGL
find_package(OpenGL REQUIRED)   
if (NOT OPENGL_FOUND)
    message (FATAL_ERROR "OpenGL not found!")
    return()
endif ()

# glew
if (UNIX)
    set(GLEW_LIBRARY libGLEW.so)                
else()
    set (GLEW_INCLUDE_DIR "" CACHE PATH "glew include directory")
    set (GLEW_LIBRARY_DIR "" CACHE PATH "glew build directory")
    if (GLEW_INCLUDE_DIR STREQUAL  "" AND GLEW_LIBRARY_DIR STREQUAL  "")
        return()
    else()
        find_library(GLEW_LIBRARY NAMES GLEW glew32 glew glew32s PATHS ${GLEW_LIBRARY_DIR})
    endif() 
endif(UNIX)

# glfw
set (GLFW_STATIC FALSE CACHE BOOL "link against static or dynamic glfw3 library")
if (WIN32)
    set (GLFW_INCLUDE_DIR "" CACHE PATH "GLFW include directory")
    set (GLFW_LIBRARY_DIR "" CACHE PATH "GLFW build directory")
    if (GLFW_INCLUDE_DIR STREQUAL "" AND GLFW_LIBRARY_DIR STREQUAL  "")
        return()
    else()
        if (GLFW_STATIC)
            find_library(GLFW_LIBS NAMES glfw3 PATHS ${GLFW_LIBRARY_DIR})
        else(GLFW_STATIC)
            find_library(GLFW_LIBS NAMES glfw3dll PATHS ${GLFW_LIBRARY_DIR})
        endif(GLFW_STATIC)  
    endif() 
else()
    find_package(PkgConfig REQUIRED)
    pkg_search_module(GLFW REQUIRED glfw3)
    if (GLFW_STATIC)
        set (GLFW_LIBS ${GLFW_STATIC_LIBRARIES})
    else(GLFW_STATIC)
        set (GLFW_LIBS ${GLFW_LIBRARIES})
    endif(GLFW_STATIC)
    list(APPEND GLFW_LIBS libXxf86vm.so)    
    list(APPEND GLFW_LIBS libGLU.so)        
    list(APPEND GLFW_LIBS libX11.so)
    list(APPEND GLFW_LIBS libXrandr.so)
    list(APPEND GLFW_LIBS libpthread.so)
    list(APPEND GLFW_LIBS libXi.so)
endif()

include_directories(${GLEW_INCLUDE_DIR}
                ${GLFW_INCLUDE_DIR}
                    ${OPENGL_INCLUDE_DIR}
                )

# executable
add_executable(${project_name} ${SOURCES} ${HEADERS})

target_link_libraries(${project_name} 
                      ${OPENGL_LIBRARIES}
                  ${GLEW_LIBRARY}
                  ${EXTRA_LIBS}
                  ${GLFW_LIBS}
                      )

如果我手动运行 ld 命令并添加 -L/usr/local/lib 则链接器运行良好。所以我最重要的问题是,如何确保 cmake 将此路径添加到 makefile 以便 ld 运行良好。

提前致谢 =)

Edit1:根据请求,带有详细日志记录的标准输出:

myname@fxt ~/courses/Modellierung/proj/exercise1 $ make VERBOSE=1
/usr/bin/cmake -H/home/myname/courses/Modellierung/proj/exercise1 -B/home/myname/courses/Modellierung/proj/exercise1 --check-build-system CMakeFiles/Makefile.cmake 0
/usr/bin/cmake -E cmake_progress_start /home/myname/courses/Modellierung/proj/exercise1/CMakeFiles /home/myname/courses/Modellierung/proj/exercise1/CMakeFiles/progress.marks
make -f CMakeFiles/Makefile2 all
make[1]: Entering directory `/home/myname/courses/Modellierung/proj/exercise1'
make -f CMakeFiles/modeling_2014_framework.dir/build.make CMakeFiles/modeling_2014_framework.dir/depend
make[2]: Entering directory `/home/myname/courses/Modellierung/proj/exercise1'
cd /home/myname/courses/Modellierung/proj/exercise1 && /usr/bin/cmake -E cmake_depends "Unix Makefiles" /home/myname/courses/Modellierung/proj/exercise1 /home/myname/courses/Modellierung/proj/exercise1 /home/myname/courses/Modellierung/proj/exercise1 /home/myname/courses/Modellierung/proj/exercise1 /home/myname/courses/Modellierung/proj/exercise1/CMakeFiles/modeling_2014_framework.dir/DependInfo.cmake --color=
make[2]: Leaving directory `/home/myname/courses/Modellierung/proj/exercise1'
make -f CMakeFiles/modeling_2014_framework.dir/build.make CMakeFiles/modeling_2014_framework.dir/build
make[2]: Entering directory `/home/myname/courses/Modellierung/proj/exercise1'
Linking CXX executable modeling_2014_framework
/usr/bin/cmake -E cmake_link_script CMakeFiles/modeling_2014_framework.dir/link.txt --verbose=1
/usr/bin/g++   -g3 -gdwarf-2    CMakeFiles/modeling_2014_framework.dir/main.cpp.o CMakeFiles/modeling_2014_framework.dir/src/VertexBufferObjectAttribs.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Vector3.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Shader.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Matrix4x4.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Scene.cpp.o CMakeFiles/modeling_2014_framework.dir/src/TgaLoader.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Vector4.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Vector2.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Renderer.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Matrix3x3.cpp.o CMakeFiles/modeling_2014_framework.dir/src/Common.cpp.o CMakeFiles/modeling_2014_framework.dir/src/SkyCube.cpp.o  -o modeling_2014_framework -rdynamic -lGLU -lGL -lSM -lICE -lX11 -lXext -lGLEW -lglfw3 -lXxf86vm -lGLU -lX11 -lXrandr -lpthread -lXi 
/usr/bin/ld: error: cannot find -lglfw3
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:49: error: undefined reference to 'glfwInit'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:53: error: undefined reference to 'glfwInit'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:60: error: undefined reference to 'glfwSetErrorCallback'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:63: error: undefined reference to 'glfwWindowHint'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:64: error: undefined reference to 'glfwWindowHint'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:65: error: undefined reference to 'glfwWindowHint'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:66: error: undefined reference to 'glfwWindowHint'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:74: error: undefined reference to 'glfwCreateWindow'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:77: error: undefined reference to 'glfwSetKeyCallback'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:78: error: undefined reference to 'glfwSetWindowSizeCallback'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:79: error: undefined reference to 'glfwSetMouseButtonCallback'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:80: error: undefined reference to 'glfwSetCursorPosCallback'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:81: error: undefined reference to 'glfwSetScrollCallback'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:84: error: undefined reference to 'glfwMakeContextCurrent'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:164: error: undefined reference to 'glfwTerminate'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:170: error: undefined reference to 'glfwGetTime'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:171: error: undefined reference to 'glfwGetTime'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:189: error: undefined reference to 'glfwPollEvents'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:190: error: undefined reference to 'glfwSwapBuffers'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:192: error: undefined reference to 'glfwSetWindowTitle'
/home/myname/courses/Modellierung/proj/exercise1/main.cpp:186: error: undefined reference to 'glfwWindowShouldClose'
/home/myname/courses/Modellierung/proj/exercise1/src/Renderer.cpp:61: error: undefined reference to 'glfwGetTime'
/home/myname/courses/Modellierung/proj/exercise1/src/Renderer.cpp:64: error: undefined reference to 'glfwGetTime'
collect2: error: ld returned 1 exit status
make[2]: *** [modeling_2014_framework] Error 1
make[2]: Leaving directory `/home/myname/courses/Modellierung/proj/exercise1'
make[1]: *** [CMakeFiles/modeling_2014_framework.dir/all] Error 2
make[1]: Leaving directory `/home/myname/courses/Modellierung/proj/exercise1'
make: *** [all] Error 2
myname@fxt ~/courses/Modellierung/proj/exercise1 $ 

编辑/快速破解解决方案: 我认为这不是原始问题的真正答案,但至少我找到了解决方法。我加了

SET( CMAKE_EXE_LINKER_FLAGS   "-L/usr/local/lib")

到 CMakeLists.txt 文件,直接在 add_executable(...) 上方

现在它可以工作了,因为 -L... 选项已正确传递给链接器。但是,由于我已经硬编码了路径,这可能不适用于任何计算机。

【问题讨论】:

  • 你能make VERBOSE=1 在这里复制失败的命令吗?
  • 是的,我已将其附加到原始帖子中。 :-)

标签: c++ linker makefile cmake ld


【解决方案1】:

您似乎缺少链接命令行中的库搜索目录。试试类似的东西。

LINK_DIRECTORIES(${GLFW_LIBRARY_DIR})

在成功找到 GLFW 库之后和add_executable之前

http://www.cmake.org/cmake/help/v2.8.12/cmake.html#command:link_directories

【讨论】:

  • 嗯,那个错误还是一样的(我之前从构建目录运行了 cmake ..,以更新 makefile)。我试过 cmake -LAH 打印出所有变量,但没有一个名为 GLFW_LIBRARY_DIR 的变量。我看到的唯一一个名为 GLFW 的变量是 GLFW_STATIC:BOOL=OFF。我在 add_executable 之前添加了 LINK_DIRECTORIES(...)。
  • 你是否也删除了缓存?
  • 是的,事实上,我一开始就尝试过,后来也使用了一个完全新鲜/空的构建文件夹。两者都失败了。我也用 cmake-gui 做到了这一点,我想知道变量 GLFW_LIBRARY_DIR 也没有显示在那里是否正常?
  • 尝试运行sudo ldconfig 看看它是否有任何改变
  • 输出是:sudo ldconfig -v | grep -i glfw --> libglfw.so.2 -> libglfw.so.2.6 虽然仍然失败
猜你喜欢
  • 2018-02-07
  • 2013-10-24
  • 2023-03-11
  • 1970-01-01
  • 2017-07-30
  • 1970-01-01
  • 1970-01-01
  • 2012-04-22
  • 2017-06-29
相关资源
最近更新 更多