Search code examples
cmakestatic-librariesstatic-linking

cmake ignores static library link request


I've searched hours on how to solve this and everything I tried did not work. I'm trying to link statically with certain libraries, (libPoco, libmysqlcpp, libmysqlclient, libssl).

I'm using cmake, and although I am defining the static library, cmake simply looks up the dynamic one. I know I have all the required libraries in static archive in my filesystem, and I know where they are.

set(CMAKE_LIBRARY_PATH ${CMAKE_LIBRARY_PATH}
              /lib
              /usr/lib
              /usr/lib64
              /usr/local/lib
              /usr/local/lib64
              /usr/lib/x86_64-linux-gnu)

find_library(POCO_NET NAMES libPocoNet.a PATHS CMAKE_LIBRARY_PATH STATIC IMPORTED)
find_library(POCO_UTIL NAMES libPocoUtil.a PATHS CMAKE_LIBRARY_PATH STATIC IMPORTED)
find_library(POCO_XML NAMES libPocoXML.a PATHS CMAKE_LIBRARY_PATH STATIC IMPORTED)
find_library (MYSQL_CLIENT NAMES libmysqlclient.a PATHS CMAKE_LIBRARY_PATH STATIC IMPORTED)
find_library (MYSQL_CPP NAMES libmysqlpp.a PATHS CMAKE_LIBRARY_PATH STATIC IMPORTED)
find_library (LIBSSL NAMES libssl.a PATHS CMAKE_LIBRARY_PATH STATIC IMPORTED)

if (POCO_NET AND POCO_UTIL AND POCO_XML AND MYSQL_CLIENT AND MYSQL_CPP AND LIBSSL)
  message(STATUS ${POCO_NET})
  message(STATUS ${POCO_UTIL})
  message(STATUS ${POCO_XML})
  message(STATUS ${MYSQL_CLIENT})
  message(STATUS ${MYSQL_CPP})
  message(STATUS ${LIBSSL})
  target_link_libraries(icarus 
            PocoNet
            PocoUtil
            PocoXML
            mysqlpp
            mysqlclient
            ssl)
else ()
  message(FATAL_ERROR "FATAL ERROR: missing library")
endif (POCO_NET AND POCO_UTIL AND POCO_XML AND MYSQL_CLIENT AND MYSQL_CPP AND LIBSSL)

But when I run cmake .. all I get is:

-- /usr/local/lib/libPocoNet.so
-- /usr/local/lib/libPocoUtil.so
-- /usr/local/lib/libPocoXML.so
-- /usr/lib/x86_64-linux-gnu/libmysqlclient.so
-- /usr/lib/libmysqlpp.so
-- /usr/lib/libssl.so

And when I try to compile, I get undefined references since I am using a -static flag. What am I missing here? Is there a way to force cmake to lookup the static libraries instead of the dynamic ones? Am I going the wrong way about this? Thank you.


Solution

  • It looks like you're getting a wee bit confused between the add_library and find_library commands. find_library doesn't take arguments of STATIC or IMPORTED.

    Also, you've not wrapped CMAKE_LIBRARY_PATH in ${} inside your find_library call, so you're effectively passing 3 paths of "CMAKE_LIBRARY_PATH", "STATIC" and "IMPORTED" to CMake's search routine, not the intended 6 paths of ${CMAKE_LIBRARY_PATH}.

    Finally, since ${CMAKE_LIBRARY_PATH} is already the first port of call in CMake search routine, there's no need to add it explicitly to the find_library commands.

    So you can do something like:

    set(CMAKE_LIBRARY_PATH ${CMAKE_LIBRARY_PATH}
                  /lib
                  /usr/lib
                  /usr/lib64
                  /usr/local/lib
                  /usr/local/lib64
                  /usr/lib/x86_64-linux-gnu)
    
    find_library(POCO_NET NAMES libPocoNet.a)
    find_library(POCO_UTIL NAMES libPocoUtil.a)
    find_library(POCO_XML NAMES libPocoXML.a)
    find_library(MYSQL_CLIENT NAMES libmysqlclient.a)
    find_library(MYSQL_CPP NAMES libmysqlpp.a)
    find_library(LIBSSL NAMES libssl.a PATHS)
    
    if(POCO_NET AND POCO_UTIL AND POCO_XML AND MYSQL_CLIENT AND MYSQL_CPP AND LIBSSL)
      message(STATUS ${POCO_NET})
      message(STATUS ${POCO_UTIL})
      message(STATUS ${POCO_XML})
      message(STATUS ${MYSQL_CLIENT})
      message(STATUS ${MYSQL_CPP})
      message(STATUS ${LIBSSL})
      target_link_libraries(icarus 
                ${POCO_NET}
                ${POCO_UTIL}
                ${POCO_XML}
                ${MYSQL_CLIENT}
                ${MYSQL_CPP}
                ${LIBSSL})
    else()
      message(FATAL_ERROR "FATAL ERROR: missing library")
    endif()