1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-27 02:57:44 +00:00

Meta: Resolve cyclic dependency between LibPthread and libc++

libc++ uses a Pthread condition variable in one of its initialization
functions. This means that Pthread forwarding has to be set up in LibC
before libc++ can be initialized. Also, because LibPthread is written in
C++, (at least some) parts of the C++ standard library have to be linked
against it.

This is a circular dependency, which means that the order in which these
two libraries' initialization functions are called is undefined. In some
cases, libc++ will come first, which will then trigger an assert due to
the missing Pthread forwarding.

This issue isn't necessarily unique to LibPthread, as all libraries that
libc++ depends on exhibit the same circular dependency issue.

The reason why this issue didn't affect the GNU toolchain is that
libstdc++ is always linked statically. If we were to change that, I
believe that we would run into the same issue.
This commit is contained in:
Daniel Bertalan 2021-11-08 19:06:02 +01:00 committed by Linus Groh
parent 62169fda03
commit fe1726521a
2 changed files with 8 additions and 5 deletions

View file

@ -47,8 +47,15 @@ function(serenity_libc target_name fs_name)
add_library(${target_name} SHARED ${SOURCES})
install(TARGETS ${target_name} DESTINATION usr/lib)
set_target_properties(${target_name} PROPERTIES OUTPUT_NAME ${fs_name})
if (CMAKE_CXX_COMPILER_ID MATCHES "Clang$")
# Avoid creating a dependency cycle between system libraries and the C++ standard library. This is necessary
# to ensure that initialization functions will be called in the right order (libc++ must come after LibPthread).
if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
target_link_options(${target_name} PRIVATE -static-libstdc++)
elseif (CMAKE_CXX_COMPILER_ID MATCHES "Clang$")
target_link_libraries(${target_name} clang_rt.builtins)
# FIXME: Implement -static-libstdc++ in the next toolchain update.
target_link_options(${target_name} PRIVATE -nostdlib++ -Wl,-Bstatic -lc++ -Wl,-Bdynamic)
target_link_options(${target_name} PRIVATE -Wl,--no-dependent-libraries)
endif()
target_link_directories(LibC PUBLIC ${CMAKE_CURRENT_BINARY_DIR})
serenity_generated_sources(${target_name})

View file

@ -123,10 +123,6 @@ add_custom_command(
set(SOURCES ${LIBC_SOURCES} ${AK_SOURCES} ${ELF_SOURCES} ${ASM_SOURCES})
if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -static-libstdc++")
endif()
# Prevent GCC from removing null checks by marking the `FILE*` argument non-null
set_source_files_properties(stdio.cpp PROPERTIES COMPILE_FLAGS "-fno-builtin-fputc -fno-builtin-fputs -fno-builtin-fwrite")