0

I have a project to use some third party libraries. This project is supposed to be for both Windows and Linux.

Due to historical reasons, the third party libraries are pre-built libraries for both Linux and Windows, the structure of the third party libraries like this:

  • Includes: $(THIRDPARTY)/Foo/include
  • Windows Libraries:
    • 32 bit Debug: $(THIRDPARTY)/Foo/lib/Win32/Debug/Foo_d.lib
    • 32 bit Release: $(THIRDPARTY)/Foo/lib/Win32/Release/Foo.lib
    • 64 bit Debug: $(THIRDPARTY)/Foo/lib/Win64/Debug/Foo_d.lib
    • 64 bit Release: $(THIRDPARTY)/Foo/lib/Win64/Release/Foo.lib
  • Linux Libraries:
    • 64 bit Debug: $(THIRDPARTY)/Foo/lib/Linux/Debug/libFoo.a
    • 64 bit Release: $(THIRDPARTY)/Foo/lib/Linux/Release/libFoo.a

Simplified project structure: Hello:

  • src/CMakeLists.txt
  • src/Hello.cpp

CMakeLists.txt for the project:

cmake_minimum_required(VERSION 3.16)

project(Hello)

set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)


add_executable(Hello)
target_sources(Hello PRIVATE ${CMAKE_SOURCE_DIR}/Hello.cpp)

target_include_directories(Hello PRIVATE ${Foo_INCLUDE_DIR})
target_link_directories(Hello PRIVATE ${Foo_LIBRARY_DIR})
target_link_libraries(Hello PRIVATE ${Foo_LIBRARIES})

I expect corresponding libraries can be linked correctly when difference configurations are selected with Visual Studio, like Debug 32 bit, Debug 64 bit, Release 32 bit, and Release 64 bit; For Linux, I expect correct libraries are linked when -DCMAKE_BUILD_TYPE is passed to cmake.

Now the problem is, how I can get correct values for ${Foo_INCLUDE_DIR}, ${Foo_LIBRARY_DIR} and ${Foo_LIBRARIES} for all different libraries for both Windows and Linux without using lots of if-else to set these variables based on CMAKE_BUILD_TYPE and architecture (32 vs 64 bit)?

I have lots of similar third party libraries like these, the library path and naming conventions are different for each library due to historical reasons. There is no way to write a function to repeat all these "setting variables" steps.

Is there an elegant way like using find_package or add_library (STATIC IMPORTED) to do this? If using find_package, then how to write FindFoo.cmake or FooConfig.cmake for each third party package?

ben yu
  • 11
  • 6
  • "how I can get correct values for ${Foo_INCLUDE_DIR}, ${Foo_LIBRARY_DIR} and ${Foo_LIBRARIES} for all different libraries for both Windows and Linux without using lots of if-else to set these variables based on CMAKE_BUILD_TYPE and architecture (32 vs 64 bit)?" - You cannot. You need to use those if-else for implement library selection mechanism. Note, that `CMAKE_BUILD_TYPE` is inaccessible when generate Visual Studio project, instead use IMPORTED library with `IMPORTED_LOCATION_` property set. – Tsyvarev Mar 11 '22 at 19:39
  • Thanks @Tsyvarev. **IMPORTED_LOCATION_Debug** and **IMPORTED_LOCATION__Release** can only distinguish Debug and Release, how can I set libraries for 32 bit and 64 bit Debug? – ben yu Mar 11 '22 at 22:46
  • As I said in the previous comment, generally you need to use if/else or other sort of branches to select the library. About checking bitness of the platform, see that question: https://stackoverflow.com/questions/39258250/how-to-detect-if-64-bit-msvc-with-cmake – Tsyvarev Mar 11 '22 at 22:57

0 Answers0