emilk / emilk/loguru

CMake: Errors when linking to shared library

Open
#248 7 comments 0 reactions 0 assignees View on GitHub
Dominant language
C++
Stars
1.9k
Forks
280
Avg merge
7m
Merged PRs (30d)
4

Description

I'm trying to use Loguru as a dependency for my shared library, but it's crashing with link-time errors. I have found a workaround that solves the issue, but this should probably be fixed, or at least documented.

## Simple example:

`main.cpp`:
```c++
#include

void foo();

int main() {
LOG_F(INFO, "Hello, world!");
foo();
}
```

`library.cpp`:
```c++
#include

void foo() {
LOG_F(INFO, "Foo was called!");
}
```

`CMakeLists.txt`:
```c++
cmake_minimum_required(VERSION 3.10)

project(loguru_cmake_example CXX)

include(FetchContent)
FetchContent_Declare(LoguruGitRepo
GIT_REPOSITORY "https://github.com/emilk/loguru" # can be a filesystem path
GIT_TAG "master"
)
FetchContent_MakeAvailable(LoguruGitRepo) # defines target 'loguru::loguru'

add_library(lib SHARED library.cpp)
target_link_libraries(lib PRIVATE loguru::loguru)

add_executable(main main.cpp)
target_link_libraries(main PRIVATE loguru::loguru lib)
```

After configuring with CMake (version 3.16.3), running `make -j $(nproc)` yields:
```
/usr/bin/ld: _deps/logurugitrepo-build/libloguru.a(loguru.cpp.o): relocation R_X86_64_PC32 against symbol `_ZN6loguru19g_flush_interval_msE' can not be used when making a shared object; recompile with -fPIC
/usr/bin/ld: final link failed: bad value
collect2: error: ld returned 1 exit status
make[2]: *** [CMakeFiles/lib.dir/build.make:85: liblib.so] Error 1
make[1]: *** [CMakeFiles/Makefile2:126: CMakeFiles/lib.dir/all] Error 2
make: *** [Makefile:84: all] Error 2
```

## Workaround

This error can be fixed by adding `set(BUILD_SHARED_LIBS ON)` before the `FetchContent_MakeAvailable(...)` call. After adding this line, I get a new error:

```
/usr/bin/ld: _deps/logurugitrepo-build/libloguru.so.2.1.0: undefined reference to `dladdr'
collect2: error: ld returned 1 exit status
make[2]: *** [CMakeFiles/main.dir/build.make:86: main] Error 1
make[1]: *** [CMakeFiles/Makefile2:99: CMakeFiles/main.dir/all] Error 2
make: *** [Makefile:84: all] Error 2
```

I found that I can fix this new error by adding `set(LOGURU_STACKTRACES ON)` before the `FetchContent_MakeAvailable(...)` call.

After adding these lines, the new `CMakeLists.txt` looks like:

```
cmake_minimum_required(VERSION 3.10)

project(loguru_cmake_example CXX)

include(FetchContent)
FetchContent_Declare(LoguruGitRepo
GIT_REPOSITORY "https://github.com/emilk/loguru" # can be a filesystem path
GIT_TAG "master"
)
set(BUILD_SHARED_LIBS ON)
set(LOGURU_STACKTRACES ON)
FetchContent_MakeAvailable(LoguruGitRepo) # defines target 'loguru::loguru'

add_library(lib SHARED library.cpp)
target_link_libraries(lib PRIVATE loguru::loguru)

add_executable(main main.cpp)
target_link_libraries(main PRIVATE loguru::loguru lib)
```

And compilation now works. Note that this issue only happens when linking a shared library against loguru, static libraries and executables work fine.

How can this issue be fixed without requiring users to implement these workarounds, or at least document that these statements are necessary for shared libraries?

Contributor guide

No contributing guide indexed for this repository

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.