-1

I have a library called Print and the function println, which mimics printf. If compiled with the directive USE_DEBUG_PRINT, println actually prints something. If compiled without this define, it prints nothing.

Then I want to use this library inside another library, let's call it A. A uses Print with this directive defined. Another library, 'B', uses 'Print' without this directive, so println has different behaviors for them.

However, when compiling into an application, depending on the link order, B will use println from A, or the opposite. This happens because the println symbol is defined for both of the libs, so the linker just picks the first.

How can I, instead, make Print "private" for these libs? I don't want anyone using A or B to have access to the println function regardless, so they can just be "merged" together, keeping println out of the 1.txt files, being used only in their implementations.

I'm using Clang and CMake to generate both libs and the app. Print is an object library, while the other ones are static.

7
  • 1
    The joys of ODR violation.
    – Eljay
    Commented May 17, 2023 at 20:16
  • Are you talking about static linking or dynamic linking? Commented May 17, 2023 at 20:17
  • are they static or shared libraries? If they're static there's nothing you can do other than giving the functions different names/namespaces Commented May 17, 2023 at 20:17
  • Also, in any case, if you managed to get a definition in each library, that seems to indicate that println is an inline function. In that case you can't even prevent it being already inlined at call sites. Even if it isn't inline you would need to make sure that it is defined in a separate translation unit without any link time optimization enabled or (for dynamic linking) that -fsemantic-interposition is enabled ((for now?) default on gcc, but not clang). Commented May 17, 2023 at 20:20
  • you can link whatever version of library you want, just use make/cmake/...... and pass that define through compilation parameters
    – KIIV
    Commented May 17, 2023 at 20:34

1 Answer 1

0

I managed to solve this by doing the following:

  • Print is now an interface, containing just a header file.
  • println is marked as static.

This way, it can be included in any .cpp file, and be compiled with the options it defined without affecting other compilations.

Not the answer you're looking for? Browse other questions tagged or ask your own question.