2013-05-12 121 views
7

我试图编译下面的测试程序:无法获得GLFW链接

#include <GL/glfw.h> 

int main(int argc, char** argv) { 
    if(!glfwInit()) { 
     return -1; 
    } 

    if(!glfwOpenWindow(640, 480, 8, 8, 8, 0, 24, 0, GLFW_WINDOW)) { 
     return -1; 
    } 

    while(glfwGetWindowParam(GLFW_OPENED)) { 
     glfwSwapBuffers(); 
    } 

    return 0; 
} 

,但我总是在问候的GLFW功能undefined reference错误。

下面是我的makefile:

CXX = clang++ 
CXXFLAGS = -Wall -std=c++0x 
LDFLAGS = -lglfw 

OBJ_DIR = bin 
LIB_DIR = -L/usr/lib 
INC_DIR = -I/usr/include 

SOURCE = main.cpp 
OBJECTS = ${SOURCE:%.cpp=$(OBJ_DIR)/%.o} 
EXECUTABLE = hello 

all: init $(OBJECTS) $(EXECUTABLE) 

$(EXECUTABLE): 
    $(CXX) $(CXXFLAGS) $(LDFLAGS) $(LIB_DIR) -o [email protected] $(OBJECTS) 

$(OBJ_DIR)/%.o: %.cpp 
    $(CXX) $(INC_DIR) -c $< -o [email protected] 

init: 
    @mkdir -p "$(OBJ_DIR)" 

clean: 
    @rm -rf $(OBJ_DIR) $(EXECUTABLE) 

我肯定有glfw.hlibglfw.a/.so当我运行locate glfw我得到:

:~$ locate glfw 
/usr/include/GL/glfw.h 
/usr/lib/libglfw.a 
/usr/lib/libglfw.so 
/usr/lib/libglfw.so.2 
/usr/lib/libglfw.so.2.6 

nm /usr/lib/libglfw.a | grep glfwInit输出:

:~$ nm /usr/lib/libglfw.a | grep glfwInit 
       U _glfwInitialized 
       U _glfwInitialized 
       U _glfwInitialized 
       U _glfwInitialized 
0000000000000000 B _glfwInitialized 
0000000000000000 T glfwInit 
       U _glfwInitialized 
       U _glfwInitialized 
       U _glfwInitialized 
       U _glfwInitialized 
       U _glfwInitialized 
       U _glfwInitJoysticks 
       U _glfwInitTimer 
00000000000000c0 T _glfwInitJoysticks 
0000000000000000 T _glfwInitTimer 

和来自clang的详细消息:

clang++ -I/usr/include -c main.cpp -o bin/main.o 
clang++ -Wall -std=c++0x -Wl --verbose -lglfw -lGL -lGLU -L/usr/lib -o hello bin/main.o 
Ubuntu clang version 3.0-6ubuntu3 (tags/RELEASE_30/final) (based on LLVM 3.0) 
Target: x86_64-pc-linux-gnu 
Thread model: posix 
clang: warning: argument unused during compilation: '-std=c++0x' 
"/usr/bin/ld" -z relro --hash-style=gnu --as-needed --build-id --eh-frame-hdr -m elf_x86_64 -dynamic-linker /lib64/ld-linux-x86-64.so.2 -o hello /usr/lib/gcc/x86_64-linux-gnu/4.6/../../../x86_64-linux-gnu/crt1.o /usr/lib/gcc/x86_64-linux-gnu/4.6/../../../x86_64-linux-gnu/crti.o /usr/lib/gcc/x86_64-linux-gnu/4.6/crtbegin.o -L/usr/lib -L/usr/lib/gcc/x86_64-linux-gnu/4.6 -L/usr/lib/gcc/x86_64-linux-gnu/4.6/../../../x86_64-linux-gnu -L/lib/x86_64-linux-gnu -L/lib/../lib64 -L/usr/lib/x86_64-linux-gnu -L/usr/lib/gcc/x86_64-linux-gnu/4.6/../../../x86_64-linux-gnu -L/usr/lib/gcc/x86_64-linux-gnu/4.6/../../.. -L/lib/x86_64-linux-gnu -L/lib -L/usr/lib/x86_64-linux-gnu -L/usr/lib -lglfw -lGL -lGLU bin/main.o -lstdc++ -lm -lgcc_s -lgcc -lc -lgcc_s -lgcc /usr/lib/gcc/x86_64-linux-gnu/4.6/crtend.o /usr/lib/gcc/x86_64-linux-gnu/4.6/../../../x86_64-linux-gnu/crtn.o 
bin/main.o: In function `main': 
main.cpp:(.text+0x17): undefined reference to `glfwInit' 
main.cpp:(.text+0x76): undefined reference to `glfwOpenWindow' 
main.cpp:(.text+0x97): undefined reference to `glfwGetWindowParam' 
main.cpp:(.text+0xa7): undefined reference to `glfwSwapBuffers' 
clang: error: linker command failed with exit code 1 (use -v to see invocation) 
make: *** [hello] Error 1 

它似乎没有找到图书馆?

+0

添加'-Wl, - 详细“到”LDFLAGS“并查看是否找到了正确的库。另外,在库文件上运行'nm'以确保未定义的引用确实在库文件中。 – 2013-05-12 07:02:50

+0

我已经使用消息的输出更新了我的帖子。它似乎没有找到图书馆? – Lerp 2013-05-12 17:10:25

回答

11

问题在于glfw库在依赖它们的对象文件之前被指定给链接器。 ld搜索库仅解析它在它正在处理的文件列表中的位置知道的依赖关系。所以当ld正在搜索libglfw.a它还不知道main.oglfwInit依赖关系。 ld(默认情况下)不会再次搜索库。

尝试:

$(EXECUTABLE): 
    $(CXX) $(CXXFLAGS) $(LIB_DIR) -o [email protected] $(OBJECTS) $(LDFLAGS) 

另外,图书馆应该大概在一个LDLIBS(或LIBS)变量指定 - LDFLAGS是链接选项通常使用:

CXX = clang++ 
CXXFLAGS = -Wall -std=c++0x 
LDLIBS = -lglfw -lGL -lGLU 

OBJ_DIR = bin 
LIB_DIR = -L/usr/lib 
INC_DIR = -I/usr/include 

SOURCE = main.cpp 
OBJECTS = ${SOURCE:%.cpp=$(OBJ_DIR)/%.o} 
EXECUTABLE = hello 

all: init $(OBJECTS) $(EXECUTABLE) 

$(EXECUTABLE): 
    $(CXX) $(LDFLAGS) $(LIB_DIR) -o [email protected] $(OBJECTS) $(LDLIBS) 

$(OBJ_DIR)/%.o: %.cpp 
    $(CXX) $(INC_DIR) -c $< -o [email protected] 

init: 
    @mkdir -p "$(OBJ_DIR)" 

clean: 
    @rm -rf $(OBJ_DIR) $(EXECUTABLE) 
+0

完美!非常感谢你。 – Lerp 2013-05-12 17:55:49