I am trying to learn OpenGL, and I am a bit stuck with linking necessary libraries. NOTE: I use WSL, trying to build an executable for Windows with CMake and mingw-w64 (i686-w64-mingw32-g++
compiler).
Here is my folder structure:
build/
CMakeCache.txt
etc.
lib/
include/
GLFW/
glfw3.h
glfw3native.h
libglfw3.a
src/
main.cpp
.gitignore
CMakeLists.txt
I want to compile the main.cpp
file, and link it with libglfw3.a
(64-bit Windows pre-compiled binary from lib-mingw-w64
directory)
My main.cpp
is a sample code from GLFW website: https://www.glfw.org/documentation.html
#include <GLFW/glfw3.h>
int main(void)
{
GLFWwindow* window;
/* Initialize the library */
if (!glfwInit())
return -1;
/* Create a windowed mode window and its OpenGL context */
window = glfwCreateWindow(640, 480, "Hello World", NULL, NULL);
if (!window)
{
glfwTerminate();
return -1;
}
/* Make the window's context current */
glfwMakeContextCurrent(window);
/* Loop until the user closes the window */
while (!glfwWindowShouldClose(window))
{
/* Render here */
glClear(GL_COLOR_BUFFER_BIT);
/* Swap front and back buffers */
glfwSwapBuffers(window);
/* Poll for and process events */
glfwPollEvents();
}
glfwTerminate();
return 0;
}
CMakeLists.txt
:
cmake_minimum_required(VERSION 3.18.4)
project(opengl-triangle)
add_executable(triangle src/main.cpp)
target_include_directories(triangle PUBLIC lib/include)
find_library(
GLFW_LIB
NAMES glfw3
HINTS "${CMAKE_SOURCE_DIR}/lib"
NO_DEFAULT_PATH
)
if(NOT GLFW_LIB)
message(FATAL_ERROR "GLFW library not found")
endif()
target_link_libraries(
triangle
${GLFW_LIB}
)
When I try to build my project I get this:
$ make
-- Configuring done
-- Generating done
-- Build files have been written to: /mnt/d/Programming/Projects/opengl-test/build
Scanning dependencies of target triangle
[ 50%] Building CXX object CMakeFiles/triangle.dir/src/main.cpp.o
[100%] Linking CXX executable triangle
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0x17): undefined reference to `glfwInit'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0x56): undefined reference to `glfwCreateWindow'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0x64): undefined reference to `glfwTerminate'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0x76): undefined reference to `glfwMakeContextCurrent'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0x81): undefined reference to `glfwWindowShouldClose'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0x96): undefined reference to `_imp__glClear@4'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0xa6): undefined reference to `glfwSwapBuffers'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0xab): undefined reference to `glfwPollEvents'
/usr/bin/i686-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0xb2): undefined reference to `glfwTerminate'
collect2: error: ld returned 1 exit status
make[2]: *** [CMakeFiles/triangle.dir/build.make:104: triangle] Error 1
make[1]: *** [CMakeFiles/Makefile2:95: CMakeFiles/triangle.dir/all] Error 2
make: *** [Makefile:103: all] Error 2
If I understand correctly, this is a linking error. However, in CMakeLists.txt
I linked the library to my executable with target_link_libraries
. Why there are undefined reference
s?
I tried to build the same with MinGW without WSL, tried to link the library with full path: target_link_libraries(triangle "/mnt/d/Programming/Projects/opengl-test/lib/libglfw3.a")
. Tried this answer (wrapped #include
statement in extern "C"
. Results are the same.
I also tried to use different compiler (cmake .. -D CMAKE_C_COMPILER=x86_64-w64-mingw32-gcc -D CMAKE_CXX_COMPILER=x86_64-w64-mingw32-g++
), and undefined reference
s changed:
Scanning dependencies of target triangle
[ 50%] Building CXX object CMakeFiles/triangle.dir/src/main.cpp.o
[100%] Linking CXX executable triangle
/usr/bin/x86_64-w64-mingw32-ld: CMakeFiles/triangle.dir/src/main.cpp.o:main.cpp:(.text+0x8a): undefined reference to `__imp_glClear'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0x10f): undefined reference to `__imp_CreateDCW'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0x14e): undefined reference to `__imp_GetDeviceCaps'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0x1a3): undefined reference to `__imp_DeleteDC'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0x2e3): undefined reference to `__imp_GetDeviceCaps'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0x8db): undefined reference to `__imp_GetDeviceCaps'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0xd68): undefined reference to `__imp_CreateDCW'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0xd77): undefined reference to `__imp_GetDeviceGammaRamp'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0xd80): undefined reference to `__imp_DeleteDC'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0xe78): undefined reference to `__imp_CreateDCW'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0xe87): undefined reference to `__imp_SetDeviceGammaRamp'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_monitor.c.obj):win32_monitor.c:(.text+0xe90): undefined reference to `__imp_DeleteDC'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_window.c.obj):win32_window.c:(.text+0x1e5): undefined reference to `__imp_CreateDIBSection'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_window.c.obj):win32_window.c:(.text+0x21f): undefined reference to `__imp_CreateBitmap'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_window.c.obj):win32_window.c:(.text+0x2c8): undefined reference to `__imp_DeleteObject'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_window.c.obj):win32_window.c:(.text+0x350): undefined reference to `__imp_DeleteObject'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_window.c.obj):win32_window.c:(.text+0x3e4): undefined reference to `__imp_CreateRectRgn'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(win32_window.c.obj):win32_window.c:(.text+0x41b): undefined reference to `__imp_DeleteObject'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(wgl_context.c.obj):wgl_context.c:(.text+0x14a): undefined reference to `__imp_SwapBuffers'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(wgl_context.c.obj):wgl_context.c:(.text+0x3f6): undefined reference to `__imp_ChoosePixelFormat'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(wgl_context.c.obj):wgl_context.c:(.text+0x404): undefined reference to `__imp_SetPixelFormat'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(wgl_context.c.obj):wgl_context.c:(.text+0xb2f): undefined reference to `__imp_DescribePixelFormat'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(wgl_context.c.obj):wgl_context.c:(.text+0x108f): undefined reference to `__imp_DescribePixelFormat'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(wgl_context.c.obj):wgl_context.c:(.text+0x10aa): undefined reference to `__imp_SetPixelFormat'
/usr/bin/x86_64-w64-mingw32-ld: ../lib/libglfw3.a(wgl_context.c.obj):wgl_context.c:(.text+0x1386): undefined reference to `__imp_DescribePixelFormat'
collect2: error: ld returned 1 exit status
make[2]: *** [CMakeFiles/triangle.dir/build.make:104: triangle] Error 1
make[1]: *** [CMakeFiles/Makefile2:95: CMakeFiles/triangle.dir/all] Error 2
make: *** [Makefile:103: all] Error 2