0

I am not sure why this question is marked as a duplicate of Why does the order in which libraries are linked sometimes cause errors in GCC?. That question and this question are two totally different questions.

I have installed libcppunit-dev with apt-get on my Debian system.

$ dpkg -l libcppunit-dev
Desired=Unknown/Install/Remove/Purge/Hold
| Status=Not/Inst/Conf-files/Unpacked/halF-conf/Half-inst/trig-aWait/Trig-pend
|/ Err?=(none)/Reinst-required (Status,Err: uppercase=bad)
||/ Name                       Version            Architecture       Description
+++-==========================-==================-==================-==========================================================
ii  libcppunit-dev             1.13.2-2.1         amd64              Unit Testing Library for C++

$ dpkg -L libcppunit-dev | grep "libcppunit\."
/usr/lib/x86_64-linux-gnu/libcppunit.a
/usr/lib/x86_64-linux-gnu/libcppunit.so

I have written a simple test. Since my concern right now is only linking cppunit, I don't have a test runner yet. Ignore the lack of test runner for now. Here is my test.cpp:

#include <cppunit/extensions/HelperMacros.h>
#include <iostream>

class FooTest : public CppUnit::TestFixture
{
protected:
    void testFoo()
    {
        CPPUNIT_ASSERT_EQUAL(1 + 1, 2);
    }

private:
    CPPUNIT_TEST_SUITE(FooTest);
    CPPUNIT_TEST(testFoo);
    CPPUNIT_TEST_SUITE_END();
};

CPPUNIT_TEST_SUITE_REGISTRATION(FooTest);

int main()
{
    std::cout << "hello\n";
    return 0;
}

Dynamic linking works fine:

$ g++ -lcppunit test.cpp && ./a.out
hello

Static linking fails:

$ g++ -l:libcppunit.a test.cpp
/tmp/ccwMWIsX.o: In function `CppUnit::AdditionalMessage::~AdditionalMessage()':
test.cpp:(.text._ZN7CppUnit17AdditionalMessageD2Ev[_ZN7CppUnit17AdditionalMessageD5Ev]+0x14): undefined reference to `CppUnit::Message::~Message()'
/tmp/ccwMWIsX.o: In function `FooTest::testFoo()':
test.cpp:(.text._ZN7FooTest7testFooEv[_ZN7FooTest7testFooEv]+0x70): undefined reference to `CppUnit::SourceLine::SourceLine(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, int)'
test.cpp:(.text._ZN7FooTest7testFooEv[_ZN7FooTest7testFooEv]+0xa5): undefined reference to `CppUnit::SourceLine::~SourceLine()'
test.cpp:(.text._ZN7FooTest7testFooEv[_ZN7FooTest7testFooEv]+0xe9): undefined reference to `CppUnit::SourceLine::~SourceLine()'
/tmp/ccwMWIsX.o: In function `FooTest::getTestNamer__()':
test.cpp:(.text._ZN7FooTest14getTestNamer__Ev[_ZN7FooTest14getTestNamer__Ev]+0x41): undefined reference to `CppUnit::TestNamer::TestNamer(std::type_info const&)'

What can I do to ensure that static linking with cppunit succeeds?

Lone Learner
  • 18,088
  • 20
  • 102
  • 200

1 Answers1

1

Try to link your program and the library in another order

g++ test.cpp -l:libcppunit.a

Or

g++ test.cpp /usr/lib/x86_64-linux-gnu/libcppunit.a

Or

g++ test.cpp -static -lcppunit -Wl,-Bdynamic

The last -Wl,-Bdynamic is required to avoid static linkage of system libraries like libc++ or glibc.

Lone Learner
  • 18,088
  • 20
  • 102
  • 200
273K
  • 29,503
  • 10
  • 41
  • 64
  • `g++ test.cpp -l:libcppunit.a` led to this error: `/usr/bin/ld: /usr/lib/gcc/x86_64-linux-gnu/6/../../../x86_64-linux-gnu/libcppunit.a(AdditionalMessage.o): relocation R_X86_64_32 against symbol `__gxx_personality_v0@@CXXABI_1.3' can not be used when making a shared object; recompile with -fPIC` – Lone Learner May 15 '18 at 16:40
  • The `g++ test.cpp -static -lcppunit -dynamic` worked but generated warnings like `cc1plus: warning: unrecognized gcc debugging option: y`, `cc1plus: warning: unrecognized gcc debugging option: n`, etc. – Lone Learner May 15 '18 at 16:43
  • `g++ test.cpp -l:libcppunit.a -fPIC` also led to this error: `/usr/bin/ld: /usr/lib/gcc/x86_64-linux-gnu/6/../../../x86_64-linux-gnu/libcppunit.a(AdditionalMessage.o): relocation R_X86_64_32 against symbol `__gxx_personality_v0@@CXXABI_1.3' can not be used when making a shared object; recompile with -fPIC`. – Lone Learner May 15 '18 at 16:48
  • I am using g++ 6.3.0. – Lone Learner May 15 '18 at 16:48
  • `g++ test.cpp /usr/lib/x86_64-linux-gnu/libcppunit.a` leads to: `/usr/bin/ld: /usr/lib/x86_64-linux-gnu/libcppunit.a(AdditionalMessage.o): relocation R_X86_64_32 against symbol `__gxx_personality_v0@@CXXABI_1.3' can not be used when making a shared object; recompile with -fPIC` – Lone Learner May 15 '18 at 16:57
  • `g++ test.cpp -static -lcppunit -Wl,-Bdynamic && ./a.out` leads to this error: `bash: ./a.out: No such file or directory`. – Lone Learner May 15 '18 at 16:58
  • Do you know why then `g++ test.cpp -static -lcppunit` works fine? – Lone Learner May 15 '18 at 16:59
  • It works fine because of libc++ is linked statically too. But libcppunit.a does not want to link with dynamic libc++. – 273K May 15 '18 at 17:03