Hide filesystem symbols used in a shared library from linking applications under gcc 8 WITHOUT specifying experimental filesystem linker flag

50 views Asked by At

I have 3 cmake targets relevant to this problem in my project.

  • Executable - The thing giving me filesystem linker errors
  • Shared Library - Core library. Originally used filesystem directly before it was abstracted
  • Static Library - naive attempt to abstract filesystem symbols hidden under private implementations and various different linker configurations. Not successful.

I do not want to require my GCC 8 consumers to require the flag -lstdc++fs but I also want to use the "experimental" yet not std::filesystem.

No matter what I do I still get this when linking the executable:

[100%] Linking CXX executable g++-8.3.1/bin/executable-d
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::status(std::filesystem::path const&)'
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::filesystem_error::~filesystem_error()'
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::path::replace_extension(std::filesystem::path const&)'
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::path::replace_filename(std::filesystem::path const&)'
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::path::_M_find_extension() const'
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::path::compare(std::filesystem::path const&) const'
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::filesystem_error::_M_gen_what()'
g++-8.3.1/lib/libShared-d.so: undefined reference to `std::filesystem::path::_M_split_cmpts()'
g++-8.3.1/lib/libShared-d.so: undefined reference to `typeinfo for std::filesystem::filesystem_error'
g++-8.3.1/lib/libShared-d.so: undefined reference to `vtable for std::filesystem::filesystem_error'
collect2: error: ld returned 1 exit status
objdump -TC libShared-d.so 

libShared-d.so:     file format elf64-x86-64

DYNAMIC SYMBOL TABLE:
0000000000000000      D  *UND*  0000000000000000              vtable for std::filesystem::filesystem_error

etc.

I do not understand why this symbol is trying to be exported. Filesystem is not exposed anywhere on the API. Side question: Is this because the gcc 8 filesystem is in an external library?

Realistically I want to have my cake and eat it, but I want to believe this is possible.

I have tried:

stripping the static lib strip --strip-unneeded libStatic-d.a

All of this junk on the Static lib (usually not all at the same time when I was testing)


    set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fvisibility=hidden")
    set_target_properties(${TARGET_NAME} PROPERTIES CXX_VISIBILITY_PRESET hidden)
    set_target_properties(${TARGET_NAME} PROPERTIES LINK_FLAGS_RELEASE -s)
    target_link_options(${TARGET_NAME} PRIVATE "-fvisibility=hidden")
    target_link_options(${TARGET_NAME} PRIVATE "--version-script=${CMAKE_CURRENT_SOURCE_DIR}/export-symbols.version")

and

add_custom_command(TARGET ${TARGET_NAME} 
    POST_BUILD
    COMMAND strip --strip-unneeded  $<TARGET_FILE:${TARGET_NAME}>
)

This on the Shared Lib

    target_link_options(${TARGET_NAME} PRIVATE "--exclude-libs,ALL")
    target_compile_options(${TARGET_NAME} PRIVATE "-Wl,--exclude-libs,ALL")

Maybe I'm just ignorant and need someone to correct me.


Edit:

ldd output

ldd libShared-d.so
libShared-d.so:
        linux-vdso.so.1 =>  (0x00007ffd791b7000)
        libdl.so.2 => /lib64/libdl.so.2 (0x00007fb088e40000)
        libicuuc.so.50 => /lib64/libicuuc.so.50 (0x00007fb088ac7000)
        libstdc++.so.6 => /lib64/libstdc++.so.6 (0x00007fb0887bf000)
        libm.so.6 => /lib64/libm.so.6 (0x00007fb0884bd000)
        libgcc_s.so.1 => /lib64/libgcc_s.so.1 (0x00007fb0882a7000)
        libpthread.so.0 => /lib64/libpthread.so.0 (0x00007fb08808b000)
        libc.so.6 => /lib64/libc.so.6 (0x00007fb087cbd000)
        /lib64/ld-linux-x86-64.so.2 (0x00007fb0899b5000)
        libicudata.so.50 => /lib64/libicudata.so.50 (0x00007fb0866ea000)

Edit 2:

ldd -d libShared-d.so
libShared-d.so:
        linux-vdso.so.1 =>  (0x00007fff1c158000)
        libdl.so.2 => /lib64/libdl.so.2 (0x00007f28aadf6000)
        libicuuc.so.50 => /lib64/libicuuc.so.50 (0x00007f28aaa7d000)
        libpthread.so.0 => /lib64/libpthread.so.0 (0x00007f28aa861000)
        libstdc++.so.6 => /lib64/libstdc++.so.6 (0x00007f28aa559000)
        libm.so.6 => /lib64/libm.so.6 (0x00007f28aa257000)
        libgcc_s.so.1 => /lib64/libgcc_s.so.1 (0x00007f28aa041000)
        libc.so.6 => /lib64/libc.so.6 (0x00007f28a9c73000)
        /lib64/ld-linux-x86-64.so.2 (0x00007f28ab96c000)
        libicudata.so.50 => /lib64/libicudata.so.50 (0x00007f28a86a0000)
undefined symbol: _ZNSt10filesystem16filesystem_errorD1Ev       (./libShared-d.so)
undefined symbol: _ZTINSt10filesystem16filesystem_errorE        (./libShared-d.so)
undefined symbol: _ZTVNSt10filesystem16filesystem_errorE        (./libShared-d.so)
0

There are 0 answers