c++cmakelinkertarget-link-libraries

CMake `add_executable` and `target_link_libraries` throwing linking error


I am following Asio tutorial by javidx9 and using CMake to link my executables and libraries. Complete source code is available in this repository.

I am facing a linking error with the executables Server.cpp and Client.cpp in folder

- Source
---- Main
-------- Server.cpp
-------- Client.cpp

In the main function if I create the class object CustomServer which inherits from ServerInterface

int main ()
{
    CustomServer server(60000);
    return 0;
}

I get following linking error:

Undefined symbols for architecture x86_64:
  "Tachys::Networking::ServerInterface<CustomMessageTypes>::ServerInterface(unsigned short)", referenced from:
      CustomServer::CustomServer(unsigned short) in Server.cpp.o
  "Tachys::Networking::ServerInterface<CustomMessageTypes>::~ServerInterface()", referenced from:
      CustomServer::~CustomServer() in Server.cpp.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make[2]: *** [Source/Main/exe_server] Error 1
make[1]: *** [Source/Main/CMakeFiles/exe_server.dir/all] Error 2
make: *** [all] Error 2

But I have used add_executable in the CMakeList.txt at:

- Source
---- Main
-------- CMakeLists.txt

and target_link_libraries in the main CMakeLists.txt at:

- CMakeLists.txt

It seems like these are the only two functions required to create an executable and link it to a created library but I am still getting this linking error and not able to figure out what to change. Please help.


Solution

  • You have template ServerInterface<CustomMessageTypes> implemented in a source file. Either move the implementation to a header, which is usually what you do, or provide the symbol ServerInterface<CustomMessageTypes> by explicitly instantianting the template in source file. See Why can templates only be implemented in the header file? and other endless online resources.

    __Start__ 
    

    Identifiers starting with double underscores are reserved. You are can't use them in your code.